Подтвердить что ты не робот

Что может пойти не так, если не удается переопределить GetHashCode() при переопределении Equals()?

Возможный дубликат:
Почему важно переопределить GetHashCode, когда метод Equals переопределен?

В С#, что конкретно может пойти не так, если не удается переопределить GetHashCode() при переопределении Equals()?

4b9b3361

Ответ 1

Наиболее заметным способом является отображение структур.

Любой класс, который делает это, будет иметь непредсказуемое поведение при использовании в качестве ключа для словаря или HashTable. Причина в том, что реализация использует как GetHashCode, так и Equals для правильного поиска значения в таблице. Краткая версия алгоритма следующая

  • Возьмите модуль HashCode по количеству ведер и индексу bucket
  • Вызовите .Equals() для указанного ключа и каждого ключа в конкретном ведре.
  • Если есть совпадение, которое является значением, нет соответствия = нет значения.

Неспособность синхронизировать GetHashCode и Equals полностью нарушит этот алгоритм (и многие другие).

Ответ 3

Подумайте о структуре хеш-словаря как о наборе нумерованных ковшей. Если вы всегда помещаете вещи в ведро, соответствующие их GetHashCode(), вам нужно искать только одно ведро (используя Equals()), чтобы увидеть, есть ли что-то. Это работает, если вы смотрите в нужное ведро.

Итак, это правило: если Equals() говорит, что два объекта равно Equal(), они должны иметь один и тот же GetHashCode().

Ответ 4

Если вы не переопределяете GetHashCode, все, что сравнивает ваши объекты, может ошибиться.

Как документировано, что GetHashCode должно возвращать одно и то же значение, если два экземпляра равны, тогда это прерогатива любого кода, который хочет проверить их на равенство, чтобы использовать GetHashCode в качестве первого прохода для групповых объектов, которые может быть одинаковым (поскольку он знает, что объекты с разными хэш-кодами не могут быть равны). Если ваш метод GetHashCode возвращает разные значения для равных объектов, то они могут попадать в разные группы в первый проход и никогда не сравниваться с использованием метода Equals.

Это может повлиять на структуру данных типа коллекций, но будет особенно проблематичным в таких хэш-кодах, как словари и хэш-наборы.

Вкратце: всегда переопределяйте GetHashCode при переопределении Equals и убедитесь, что их реализации согласованы.

Ответ 5

Любой алгоритм, который использует Ключ, не сможет работать, полагая, что он полагается на предполагаемое поведение хеш-ключей.

Два объекта с Equal должны иметь одно и то же значение ключа хеширования, которое не удалено по умолчанию по умолчанию.