web-dev-qa-db-ja.com

ほとんどの言語で最大ヒープではなく最小ヒープが実装されているのはなぜですか?

気がついたのですが、何か理由があるのでしょうか。 C++(std :: priority_queueは最大ヒープです)を除いて、最大ヒープを提供する他の言語は知りません。

Pythonのheapqモジュールは、リストの上にバイナリmin-heapを実装します。

Javaのライブラリには、min-priority-queueを実装するPriorityQueueクラスが含まれています。

Goのライブラリには、互換性のあるデータ構造の上に最小ヒープを実装するコンテナー/ヒープモジュールが含まれています。

AppleのCore Foundationフレームワークには、最小ヒープを実装するCFBinaryHeap構造が含まれています。

最大ヒープの方が最小ヒープよりも直感的であることがわかりました。技術的には、実装の違いは比較演算子の変更の問題にすぎないと思います。本当の理由はありますか?ほとんどのアプリケーションで、最大ヒープではなく最小ヒープが必要ですか?前もって感謝します

19
Bernardo Pires

他の人が観察したように、ヒープがコンパレータを受け入れる場合、どちらか一方の動作を取得することはそれほど難しくありません。ただし、Google Codeをざっと見てみると、2つのアプリケーションが繰り返し登場するため、実際のコードではmin-heapがはるかに普及していることがわかります。

  • Dijkstra/A * /他の多くの最短経路アルゴリズム(部分経路が長くなるため)。

  • イベントシミュレーション(時間が進むため)。

また、デフォルトのソートではアイテムが小さいものから大きいものまで返されるため、デフォルトのヒープも返されると私は主張します。

9
slowpoke

それは単に好みの問題です。特に理由はないと思います。最適化の問題をコストの最小化として表現したい人もいれば、利益を最大化したい人もいます。

5
Charles Peng

私が知っているほとんどの言語では、パラメーターを渡して最小ヒープと最大ヒープのどちらにするかを決定できます。したがって、デフォルト値はやや恣意的です。ほとんどの言語では、デフォルトの演算子を定義することは一貫性の問題だと思います。 stlのC++の場合、デフォルトはstd::lessであり、最小ヒープにつながります。

すべての場所でデフォルトでstd::lessを使用する一貫性は、あらゆる種類のデータ構造を使用している場合にのみこの比較を実装する必要があり、後で設計するときにどのデータ構造を使用するかを決定する必要がないことを意味しますクラス。他の言語でも同じだと思いますが、大なり比較が標準であるという唯一の違いがあります。

3
LiKao

基本的に、インデックス値は任意の数値です。数値が優先度を表し、数値が大きいほど優先度が高いと思われる場合は、最大ヒープが理にかなっています。しかし、数値がたとえばベーカリーの概念的な数値( "Take a number")を表す場合、min-heapはより理にかなっています。

インデックスの1の補数を取ることで、常に一方から他方に変換できます。

1
Daniel R Hicks