複雑さの観点から、ハッシュテーブルとディクショナリが C# でどのように機能するかをよりよく理解しようとしています (ただし、言語は重要な要素ではないと思います。これはおそらく理論的な問題にすぎません)。
Add
a のメソッドは、容量よりも小さいDictionary
場合は O(1) であると想定されていることを知っていCount
ます (これは明らかです)。
ただし、そのコードを見てみましょう。
public class Foo {
public Foo() { }
public override int GetHashCode() {
return 5; //arbitrary value, purposely a constant
}
}
static void Main(string[] args) {
Dictionary<Foo, int> test = new Dictionary<Foo,int>();
Foo a = new Foo();
Foo b = new Foo();
test .Add(a, 5);
test .Add(b, 6); //1. no exception raised, even though GetHashCode() returns the same hash
test .Add(a, 10); //2. exception raised
}
舞台裏ではハッシュの衝突があり、1.
おそらくそれを処理するための別の連鎖があることを理解しています。
ただし、2.
引数で例外が発生します。つまり、Dictionary は、ハッシュを決定した後に挿入された各キーを内部的に追跡します。これは、辞書にエントリを追加するたびに、メソッドを使用してキーがまだ挿入されていないかどうかを確認することも意味しますequals
。
私の質問は、既に挿入されたキーをチェックする場合、O(n) であるべきだと思われるのに、なぜ O(1) の複雑さと見なされるのですか?