|
二分ヒープ(にぶんヒープ,バイナリヒープ,Binary heap)とは、二分木を使って作られるヒープ(データ構造)の特に単純な種類のひとつである。それは、二分木に、以下の2つの制約を追加したものとみなせる。 * 要素間の順序関係に従った比較によって、各々のノードはそのノードの子よりも大きいか等しくなるように配置される(heap property) * 木は完全にバランスの取れた二分木(すべての葉は同じ高さにある)になるか、木のもっとも高い方がすべて埋まっていないならば、ノードは左から右へ順に埋まっていく(shape property) ここで「より大きい」とは、比較のためにいかなる比較関数を選択するかによって意味づけられる。ノード内のデータが常に数値であるとは限らないので、数量的な『より大きい』である必要はなく、数理的に言うところの全順序であればよい。 また、heap propertyのような制約を持つ木を一般に「部分順序付き木」と言う。ヒープは、部分順序付き二分木に、さらにshape propertyの制約を加えたものである。配列を使って実装できるという特性がある(後述)。 比較が数量的な「より大きい」であるヒープは最大ヒープ (max heap) と呼ばれる。また、比較が数量的な「より小さい」であるヒープは最小ヒープ (min heap) と呼ばれる。たとえば優先順位付き待ち行列において、小さい値が高い優先度を意味するのであれば、最小ヒープを使う。 ヒープ内の子同士の順序は、heap propertyによって特定できないことに注意すること。つまり、親を同じくする二つの子は、制約を壊さない限り自由に入れ替えることができる(Treapと比較せよ)。 == ヒープ操作 == === ヒープへの追加 === すでに存在しているヒープに、前述の制約を保ったまま要素を追加するには、up-heap(bubble-up, percolate-up, sift-up, trickle-up, heapify-up, cascade-up 等とも)と呼ばれる操作によらなければならない。以下のアルゴリズムにしたがって、二分ヒープに対し O(log n) で操作を行うことができる。 # ヒープの最下層に要素を追加する # 追加した要素とその親を比較する。正しい順序で並んでいるならば、停止する。 # もし順序が正しくないならば、親と追加要素を交換して、2に戻る。 我々は、この操作をツリー上で最大各々の深さで行う必要がある。つまり、木の高さ分行う必要があるので、O(log n) かかる。しかしながら、およそ要素の50%が葉であり最下層から2レベルまでには75%の要素が含まれることから、新しい要素を挿入する際、ヒープを維持するために、上向きに2, 3レベル動かすくらいですむだろう。このように、二分ヒープは、要素の挿入には平均 O(1) の固定時間をサポートする。 我々が最大ヒープと呼んでいるものは以下のようなものである。 ::150px ここで、ヒープに「15」という数字を付け加えたい。まず最初に X の印がついている場所に「15」を置く。しかし、「15」は親である「8」より大きいのでヒープの制約条件に違反している。そこで、「15」と「8」を入れ替える。最初の入れ替え後、ヒープは以下の様になる。 ::150px しかし「15」はその親である「11」よりも大きいので、まだヒープの制約条件に違反している。そこで、再度入れ替える必要がある。 ::150px これで、適切な最大ヒープができた。 抄文引用元・出典: フリー百科事典『 ウィキペディア(Wikipedia)』 ■ウィキペディアで「二分ヒープ」の詳細全文を読む スポンサード リンク
|