Skip to content

Instantly share code, notes, and snippets.

@grevych
Last active February 15, 2019 23:04
Show Gist options
  • Save grevych/fe732c5f1e93529cd08cae082ec1e761 to your computer and use it in GitHub Desktop.
Save grevych/fe732c5f1e93529cd08cae082ec1e761 to your computer and use it in GitHub Desktop.
Stack Tracker: Limit the number of elements of a stack based in a min or max criteria.
class TrackerError(Exception):
pass
class TrackerMethodNotImplemented(TrackerError):
pass
class StackTracker(object):
def __init__(self, limit, items = None):
self.__limit__ = limit
self.__items__ = items or []
def push(self, item):
if self.current_size == 0:
self.__items__.append(item)
elif self.current_size == self.limit:
self.__cap__(item)
else:
self.__insert__(item)
return self.items
def __cap__(self, item):
raise TrackerMethodNotImplemented
def __insert__(self, item):
start = 0
end = self.current_size
index = (start + end) // 2
while start != index and end != index:
current_item = self.__items__[index]
if current_item > item:
end = index
else:
start = index
index = (start + end) // 2
if item > self.__items__[index]:
self.__items__.insert(index + 1, item)
else:
self.__items__.insert(index, item)
@property
def current_size(self):
return len(self.__items__)
@property
def items(self):
return self.__items__[:]
@property
def last(self):
return self.__items__[-1] if self.current_size else None
@property
def first(self):
return self.__items__[0] if self.current_size else None
@property
def limit(self):
return self.__limit__
class MinTracker(StackTracker):
def __cap__(self, item):
if self.last < item:
return
self.__items__.pop()
self.__insert__(item)
class MaxTracker(StackTracker):
def __cap__(self, item):
if self.first > item:
return
del self.__items__[0]
self.__insert__(item)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment