I'd like to store a set of objects in a min heap by defining a custom comparison function. I see there is a heapq module available as part of the python distribution. Is there a way to use a custom comparator with this module? If not, has someone else built a custom min heap?
A Min-Heap is a complete binary tree in which the value in each internal node is smaller than or equal to the values in the children of that node.
8 Common Data Structures every Programmer must know The heapq module of python implements the heap queue algorithm. It uses the min heap where the key of the parent is less than or equal to those of its children.
In Python, it is available using the “heapq” module. The property of this data structure in Python is that each time the smallest heap element is popped(min-heap). Whenever elements are pushed or popped, heap structure is maintained. The heap[0] element also returns the smallest element each time.
There are two types of heaps: Min-heap and Max-heap. A min-heap is used to access the minimum element in the heap whereas the Max-heap is used when accessing the maximum element in the heap.
Two options (aside from Devin Jeanpierre's suggestion):
Decorate your data before using the heap. This is the equivalent of the key=
option to sorting. e.g. if you (for some reason) wanted to heapify a list of numbers according to their sine:
data = [ # list of numbers ]
heap = [(math.sin(x), x) for x in data]
heapq.heapify(heap)
# get the min element
item = heappop(heap)[1]
The heapq
module is implemented in pure python. You could just copy it to your working directory and change the relevant bits. From a quick look, you would have to modify siftdown() and siftup(), and possibly nlargest and nsmallest if you need them.
Yes, there is a way. Define a wrapping class that implements your custom comparator, and use a list of those instead of a list of your actual objects. That's about the best there is while still using the heapq module, since it provides no key= or cmp= arguments like the sorting functions/methods do.
def gen_wrapper(cmp):
class Wrapper(object):
def __init__(self, value): self.value = value
def __cmp__(self, obj): return cmp(self.value, obj.value)
return Wrapper
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With