-
-
Save wolf81/a43680c95933198b2579c29a04a2fb84 to your computer and use it in GitHub Desktop.
Circular Buffer in Lua
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
-- circular buffer factory for lua | |
local function rotate_indice(i, n) | |
return ((i - 1) % n) + 1 | |
end | |
local circular_buffer = {} | |
local function circular_buffer:filled() | |
return #(self.history) == self.max_length | |
end | |
local function circular_buffer:push(value) | |
if self:filled() then | |
local value_to_be_removed = self.history[self.oldest] | |
self.history[self.oldest] = value | |
self.oldest = self.oldest == self.max_length and 1 or self.oldest + 1 | |
else | |
self.history[#(self.history) + 1] = value | |
end | |
end | |
circular_buffer.metatable = {} | |
-- positive values index from newest to oldest (starting with 1) | |
-- negative values index from oldest to newest (starting with -1) | |
local function circular_buffer.metatable:__index(i) | |
local history_length = #(self.history) | |
if i == 0 or math.abs(i) > history_length then | |
return nil | |
elseif i >= 1 then | |
local i_rotated = rotate_indice(self.oldest - i, history_length) | |
return self.history[i_rotated] | |
elseif i <= -1 then | |
local i_rotated = rotate_indice(i + 1 + self.oldest, history_length) | |
return self.history[i_rotated] | |
end | |
end | |
local function circular_buffer.metatable:__len() | |
return #(self.history) | |
end | |
local function circular_buffer.new(max_length) | |
if type(max_length) ~= 'number' or max_length <= 1 then | |
error("Buffer length must be a positive integer") | |
end | |
local instance = { | |
history = {}, | |
oldest = 1, | |
max_length = max_length, | |
push = circular_buffer.push, | |
filled = circular_buffer.filled, | |
} | |
setmetatable(instance, circular_buffer.metatable) | |
return instance | |
end | |
return circular_buffer |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment