Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- local function sift_up(queue, index)
- local current, parent = index, (index - (index % 2))/2
- while current > 1 and queue.cmp(queue[current][2], queue[parent][2]) do
- queue[current], queue[parent] = queue[parent], queue[current]
- current, parent = parent, (parent - (parent % 2))/2
- end
- return current
- end
- local function sift_down(queue, index)
- local current, child, size = index, 2*index, #queue
- while child <= size do
- if child < size and queue.cmp(queue[child + 1][2], queue[child][2]) then
- child = child + 1
- end
- if queue.cmp(queue[child][2], queue[current][2]) then
- queue[current], queue[child] = queue[child], queue[current]
- current, child = child, 2*child
- else
- break
- end
- end
- return current
- end
- local methods = {
- insert = function(self, element, value)
- table.insert(self, {element, value})
- return sift_up(self, #self)
- end,
- remove = function(self, element, compFunc)
- local index = self:contains(element, compFunc)
- if index then
- local size = #self
- self[index], self[size] = self[size], self[index]
- local ret = table.remove(self)
- if size > 1 and index < size then
- sift_down(self, index)
- if index > 1 then
- sift_up(self, index)
- end
- end
- return unpack(ret)
- end
- end,
- pop = function(self)
- if self[1] then
- local size = #self
- self[1], self[size] = self[size], self[1]
- local ret = table.remove(self)
- if size > 1 then
- sift_down(self, 1)
- end
- return unpack(ret)
- end
- end,
- peek = function(self)
- if self[1] then
- return self[1][1], self[1][2]
- end
- end,
- contains = function(self, element, compFunc)
- for index, entry in ipairs(self) do
- if (compFunc and compFunc(entry[1], element)) or entry[1] == element then
- return index
- end
- end
- return false
- end,
- isEmpty = function(self)
- return #self == 0
- end,
- size = function(self)
- return #self
- end,
- getValue = function(self, element, compFunc)
- local index = self:contains(element, compFunc)
- return (index and self[index][2]) or false
- end,
- setValue = function(self, element, value, compFunc)
- local index = self:contains(element, compFunc)
- if index then
- self[index][2] = value
- sift_up(self, index)
- sift_down(self, index)
- return true
- else
- return false
- end
- end,
- }
- function new(compareFunc)
- local queue = {}
- queue.cmp = type(compareFunc) == "function" and compareFunc or function(a, b) return a < b end
- setmetatable(queue, {__index = methods})
- return queue
- end
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement