Методы equals и hashCode в Java

Какую роль играют методы equals и hashCode, нужно ли их переопределять и как правильно их использовать.

Для начала разберёмся, что это за методы и в чём между ними разница.

  • equals – возвращает true если объекты одинаковые;
  • hashCode – вычисляет хэш код объекта.

По определению если два объекта одинаковы, то у них должны быть одинаковы и хэш коды. Да, это так. Но, хэш функции пока ещё не могут дать 100% гарантию того, что даже при сложном алгоритме их вычисления рано или поздно не появятся два разных объект с одинаковыми хэш кодами (то есть не возникнет так называемая коллизия). Поэтому метод hashCode не является достаточно надёжным средством для определения идентичности объектов и в дополнение к нему существует метод equals, которым и следует пользоваться при сравнении объектов.

Методы equals и hashCode определены и реализованы в классе Object.

Хороший стиль разработки предполагает переопределение этих методов. Но, многие программисты, к сожалению, этим пренебрегают и нередко можно столкнуться с тем, что даже на самом верхнем уровне абстракции в сложной иерархии классов equals и hashCode остаются неизменными.

И не было бы ничего страшного если бы equals и hashCode в Object могли каким-то образом учитывать содержимое класса, но такой возможности у них нет. Более того метод hashCode в Object реализован так, что даже у одного и того же объекта при каждом запуске программы хэш код будет разным. Поэтому, даже если возникнет необходимость просто сравнить хзш коды объектов, то получить адекватный результат при таком сравнении будет почти невозможно.

Как быть?

Первый и самый лучший способ. При создании собственных классов переопределять методы equals и hashCode. Как при переопределении будет учитываться структура класса, хранящиеся в нём данные и другие факторы, каждому программисту необходимо решать индивидуально в зависимости от задачи. Но, в любом случае собственная реализация equals и hashCode должна быть.

Если же её по каким-то причинам нет, и вы или ваш коллега оставляете всё как было изначально в Object, то лучше следовать второму способу. А, именно не использовать методы equals и hashCode вовсе. Лучше отказаться от использования методов, чем работать с некорректными результатами их выполнения.

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *