📜  Python的最大堆

📅  最后修改于: 2021-10-28 02:05:46             🧑  作者: Mango

Max-Heap 是一个完整的二叉树,其中每个内部节点中的值大于或等于该节点的子节点中的值。
将堆的元素映射到数组是微不足道的:如果一个节点存储在索引 k 中,那么它的左子节点存储在索引2k + 1 处,其右子节点存储在索引2k + 2 处

最大堆示例: 最大堆

最大堆是如何表示的?
最大堆是一棵完全二叉树。 Max heap 通常表示为一个数组。根元素将在Arr[0] 。下表显示了第 i 个节点的其他节点的索引,即Arr[i]
Arr[(i-1)/2]返回父节点。
Arr[(2*i)+1]返回左子节点。
Arr[(2*i)+2]返回右子节点。

最大堆上的操作:

  1. getMax() :它返回最大堆的根元素。此操作的时间复杂度为O(1)
  2. extractMax() :从 MaxHeap 中移除最大元素。此操作的时间复杂度为O(Log n),因为此操作需要在移除 root 后维护堆属性(通过调用 heapify())。
  3. insert() :插入新键需要O(Log n)时间。我们在树的末尾添加一个新键。如果新键小于它的父键,那么我们不需要做任何事情。否则,我们需要向上遍历以修复违反的堆属性。

注意:在下面的实现中,我们从索引 1 开始索引以简化实现。

# Python3 implementation of Max Heap
import sys
  
class MaxHeap:
  
    def __init__(self, maxsize):
          
        self.maxsize = maxsize
        self.size = 0
        self.Heap = [0] * (self.maxsize + 1)
        self.Heap[0] = sys.maxsize
        self.FRONT = 1
  
    # Function to return the position of
    # parent for the node currently
    # at pos
    def parent(self, pos):
          
        return pos // 2
  
    # Function to return the position of
    # the left child for the node currently
    # at pos
    def leftChild(self, pos):
          
        return 2 * pos
  
    # Function to return the position of
    # the right child for the node currently
    # at pos
    def rightChild(self, pos):
          
        return (2 * pos) + 1
  
    # Function that returns true if the passed
    # node is a leaf node
    def isLeaf(self, pos):
          
        if pos >= (self.size//2) and pos <= self.size:
            return True
        return False
  
    # Function to swap two nodes of the heap
    def swap(self, fpos, spos):
          
        self.Heap[fpos], self.Heap[spos] = (self.Heap[spos], 
                                            self.Heap[fpos])
  
    # Function to heapify the node at pos
    def maxHeapify(self, pos):
  
        # If the node is a non-leaf node and smaller
        # than any of its child
        if not self.isLeaf(pos):
            if (self.Heap[pos] < self.Heap[self.leftChild(pos)] or
                self.Heap[pos] < self.Heap[self.rightChild(pos)]):
  
                # Swap with the left child and heapify
                # the left child
                if (self.Heap[self.leftChild(pos)] > 
                    self.Heap[self.rightChild(pos)]):
                    self.swap(pos, self.leftChild(pos))
                    self.maxHeapify(self.leftChild(pos))
  
                # Swap with the right child and heapify
                # the right child
                else:
                    self.swap(pos, self.rightChild(pos))
                    self.maxHeapify(self.rightChild(pos))
  
    # Function to insert a node into the heap
    def insert(self, element):
          
        if self.size >= self.maxsize:
            return
        self.size += 1
        self.Heap[self.size] = element
  
        current = self.size
  
        while (self.Heap[current] > 
               self.Heap[self.parent(current)]):
            self.swap(current, self.parent(current))
            current = self.parent(current)
  
    # Function to print the contents of the heap
    def Print(self):
          
        for i in range(1, (self.size // 2) + 1):
            print(" PARENT : " + str(self.Heap[i]) + 
                  " LEFT CHILD : " + str(self.Heap[2 * i]) +
                  " RIGHT CHILD : " + str(self.Heap[2 * i + 1]))
  
    # Function to remove and return the maximum
    # element from the heap
    def extractMax(self):
  
        popped = self.Heap[self.FRONT]
        self.Heap[self.FRONT] = self.Heap[self.size]
        self.size -= 1
        self.maxHeapify(self.FRONT)
          
        return popped
  
# Driver Code
if __name__ == "__main__":
      
    print('The maxHeap is ')
      
    maxHeap = MaxHeap(15)
    maxHeap.insert(5)
    maxHeap.insert(3)
    maxHeap.insert(17)
    maxHeap.insert(10)
    maxHeap.insert(84)
    maxHeap.insert(19)
    maxHeap.insert(6)
    maxHeap.insert(22)
    maxHeap.insert(9)
  
    maxHeap.Print()
      
    print("The Max val is " + str(maxHeap.extractMax()))

输出 :

The maxHeap is 
 PARENT : 84 LEFT CHILD : 22 RIGHT CHILD : 19
 PARENT : 22 LEFT CHILD : 17 RIGHT CHILD : 10
 PARENT : 19 LEFT CHILD : 5 RIGHT CHILD : 6
 PARENT : 17 LEFT CHILD : 3 RIGHT CHILD : 9
The Max val is 84

使用库函数:

我们使用 heapq 类在Python实现堆。默认情况下,Min Heap 由此类实现。但是我们将每个值乘以 -1,以便我们可以将其用作 MaxHeap。

# Python3 program to demonstrate working of heapq
  
from heapq import heappop, heappush, heapify
  
# Creating empty heap
heap = []
heapify(heap)
  
# Adding items to the heap using heappush
# function by multiplying them with -1
heappush(heap, -1 * 10)
heappush(heap, -1 * 30)
heappush(heap, -1 * 20)
heappush(heap, -1 * 400)
  
# printing the value of maximum element
print("Head value of heap : "+str(-1 * heap[0]))
  
# printing the elements of the heap
print("The heap elements : ")
for i in heap:
    print(-1 * i, end = ' ')
print("\n")
  
element = heappop(heap)
  
# printing the elements of the heap
print("The heap elements : ")
for i in heap:
    print(-1 * i, end = ' ')

输出 :

Head value of heap : 400
The heap elements : 
400 30 20 10 

The heap elements : 
30 10 20 

如果您希望与专家一起参加现场课程,请参阅DSA 现场工作专业课程学生竞争性编程现场课程