ヒープは、特に優先度キューの実装に用いられる非常に効率的なデータ構造です。ヒープは完全二分木の特性を持ち、各ノードがその子ノードよりも優先度が高い(または低い)という特性を持っています。この特性により、最大値または最小値の取得が効率的に行えます。
ヒープには主に2つのタイプがあります。
ヒープを用いることで、優先度に基づいて要素を効率的に追加、削除、取得することができます。
ヒープにはいくつかの基本的な操作があります。
次に、Pythonでヒープを実装してみましょう。
以下は、最小ヒープの実装例です。
class MinHeap:
def __init__(self):
self.heap = []
def insert(self, value):
self.heap.append(value)
self._heapify_up(len(self.heap) - 1)
def delete_min(self):
if len(self.heap) == 0:
return None
if len(self.heap) == 1:
return self.heap.pop()
min_value = self.heap[0]
self.heap[0] = self.heap.pop() # 最後の要素をルートに移動
self._heapify_down(0)
return min_value
def get_min(self):
return self.heap[0] if self.heap else None
def _heapify_up(self, index):
parent_index = (index - 1) // 2
if index > 0 and self.heap[index] < self.heap[parent_index]:
self.heap[index], self.heap[parent_index] = self.heap[parent_index], self.heap[index]
self._heapify_up(parent_index)
def _heapify_down(self, index):
smallest = index
left_child_index = 2 * index + 1
right_child_index = 2 * index + 2
if left_child_index < len(self.heap) and self.heap[left_child_index] < self.heap[smallest]:
smallest = left_child_index
if right_child_index < len(self.heap) and self.heap[right_child_index] < self.heap[smallest]:
smallest = right_child_index
if smallest != index:
self.heap[index], self.heap[smallest] = self.heap[smallest], self.heap[index]
self._heapify_down(smallest)
def __str__(self):
return str(self.heap)
__init__
メソッド: ヒープの初期化を行います。空のリストを作成します。insert
メソッド: 新しい値をヒープに追加し、ヒープの特性を保つために、_heapify_up
メソッドを呼び出します。delete_min
メソッド: 最小値を削除し、最後の要素をルートに移動してから、_heapify_down
メソッドを呼び出してヒープの特性を保ちます。get_min
メソッド: ヒープの最小の値を返します。_heapify_up
メソッド: 新しい要素が適切な位置に来るまで親ノードと入れ替えます。_heapify_down
メソッド: ヒープの特性を保つために、子ノードと入れ替えを行います。__str__
メソッド: ヒープの内容を文字列として表示します。以下は、上記のMinHeap
クラスを使用した例です。
if __name__ == "__main__":
heap = MinHeap()
heap.insert(10)
heap.insert(4)
heap.insert(15)
heap.insert(20)
heap.insert(3)
print("Heap:", heap)
print("Minimum value:", heap.get_min())
print("Deleting minimum value:", heap.delete_min())
print("Heap after deletion:", heap)
このようにして、ヒープ(優先度キュー)の基本的な操作を理解し、実装することができます。ヒープは、スケジューリング問題やその他多くのアルゴリズムで非常に重要な役割を果たします。