ハッシュテーブルでこれらの関数の実行時の複雑さが異なるのはなぜですか?
Wikiでは、検索と削除はO(n)(ハッシュテーブルのポイントは定数検索であると考えたため、検索がO(n)の場合のポイントは何ですか))。
しばらく前のいくつかのコースノートでは、すべてのO(1)を含む特定の詳細に応じて、さまざまな複雑さが見られます。すべてのO(1)を取得できる場合、なぜ他の実装が使用されるのですか?
C++やJavaのような言語で標準のハッシュテーブルを使用している場合、時間の複雑さはどうなりますか?
ハッシュテーブル はO(1)
averageと amortized (のケースの複雑さですが、問題がありますO(n)
最悪の場合時間の複雑さ。 [そして、これがあなたの混乱があるところだと思う]
ハッシュテーブルは、次の2つの理由により、O(n)
最悪の時間の複雑さの影響を受けます。
O(n)
時間がかかる場合があります。ただし、次の理由により、O(1)
平均および償却ケースと言われています。
O(n)
である再ハッシュ操作は、すべて_n/2
_ opsの後に発生する可能性があります。これらはすべてO(1)
と想定されます。したがって、opごとの平均時間を合計すると、_(n*O(1) + O(n)) / n) = O(1)
_再ハッシュの問題-リアルタイムアプリケーションおよび低 レイテンシ を必要とするアプリケーション-のデータ構造としてハッシュテーブルを使用しないでください。
EDIT:ハッシュテーブルに関する別の問題: cache
大きなハッシュテーブルでパフォーマンスが低下する可能性がある別の問題は、キャッシュのパフォーマンスが原因です。 ハッシュテーブルはキャッシュのパフォーマンスが悪いため、したがって大規模なコレクションの場合-テーブルの関連部分をリロードする必要があるため、アクセス時間が長くなる可能性がありますメモリからキャッシュに戻ります。
理想的には、ハッシュテーブルはO(1)
です。問題は、2つのキーが等しくないが、同じハッシュになる場合です。
たとえば、文字列"最高の時間であり、最悪の時間であった"と"緑の卵とハム"が両方とも_123
_。
最初の文字列が挿入されると、バケット123に配置されます。2番目の文字列が挿入されると、バケット_123
_の値が既に存在することがわかります。次に、新しい値を既存の値と比較し、それらが等しくないことを確認します。この場合、そのキーに対して配列またはリンクリストが作成されます。この時点で、ハッシュテーブルはそのバケット内の各値を反復処理して必要な値を見つける必要があるため、この値を取得するとO(n)
になります。
このため、ハッシュテーブルを使用する場合は、高速で、異なるオブジェクトの値が重複することはほとんどない、非常に優れたハッシュ関数を持つキーを使用することが重要です。
理にかなっていますか?
一部のハッシュテーブル( カッコウハッシュ )で保証されているO(1)ルックアップ
おそらく、スペースの複雑さを見ていましたか?それはO(n)です。他の複雑さは ハッシュテーブル エントリで予想されるとおりです。バケットの数が増えると、検索の複雑度はO(1)に近づきます。最悪の場合、ハッシュテーブルにバケットが1つしかない場合、検索の複雑度はO(n)です。
コメントに応じて編集するO(1)は平均的なケースだ。(ウィキペディアのページにあるように)O(1 + n/k)ここで、Kはハッシュテーブルサイズです。Kが十分に大きい場合、結果は事実上O(1)になりますが、Kは10およびNであるとしますその場合、各バケットには平均10エントリがあるため、検索時間は間違いなくO(1)ではなく、最大10エントリの線形検索です。
ハッシュの実装方法によって異なりますが、最悪の場合はO(n)になりますが、最良の場合は0(1)(通常、DSはそれほど簡単ではありません)