минимальная куча в python

Я хотел бы сохранить набор объектов в минимальной куче, определив пользовательскую функцию сравнения. Я вижу, что есть модуль heapq, доступный как часть дистрибутива python. Есть ли способ использовать пользовательский компаратор с этим модулем? Если нет, кто-то еще построил пользовательскую минимальную кучу?

2 ответов


Да, есть способ. Определите класс обертки, реализующий пользовательский компаратор, и используйте список этих классов вместо списка реальных объектов. Это лучшее, что есть при использовании модуля heapq, поскольку он не предоставляет аргументов key= или cmp=, как это делают функции/методы сортировки.

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

два варианта (помимо предложения Девина Жанпьера):

  1. украсьте свои данные перед использованием кучи. Это эквивалент key= опция сортировки. например, если вы (по какой-то причине) хотели сложить список чисел в соответствии с их синусом:

    data = [ # list of numbers ]
    heap = [(math.sin(x), x) for x in data]
    heapq.heapify(heap)
    # get the min element
    item = heappop(heap)[1]
    
  2. на heapq модуль реализован в чистом python. Вы можете просто скопировать его в свой рабочий каталог и измените соответствующие биты. От быстрого взгляда, вы необходимо изменить siftdown () и siftup () и, возможно, nlargest и nsmallest, если они вам нужны.