В предупреждениях только сказано, что x.hashCode() != Objects.hashCode(x)
верно. (Хорошо, это верно в большинстве случаев. Они все еще могут сталкиваться для некоторых значений. На самом деле это не равно для большинства объектов.)
Допустимая реализация hashCode / equals:
public class Teacher {
private final String name;
public Teacher(String name) {
this.name = name;
}
@Override public equals(Object obj){
if(obj == this) return true;
if(!(obj instanceof Teacher)) return false;
return Objects.equal(name, ((Teacher) obj).getName());
}
@Override public hashCode(){
return 0;
}
}
Это допустимо, хотя все хеш-значения конфликтуют. Из hashCode () javadoc:
Не обязательно, если два объекта
неравны в соответствии с
метод equals (java.lang.Object), затем
вызов метода hashCode для каждого из
два объекта должны производить разные
целочисленные результаты.
Отличие от "нормальной" реализации состоит в том, что производительность этого кода будет намного хуже. Например, HashMaps выродится в списки, такие как производительность для поиска.
Даже с этой реализацией:
@Override
public int hashCode() {
return Objects.hashCode(Teacher.class, name);
}
Возможно (но очень маловероятно), что значения хеш-функции разных классов сталкиваются. Это тот случай, если хеши имен классов одинаковы для обоих классов.
Оптимизация такого рода должна быть последним средством, когда * * * * * * * * * * * * * * * * * *1025* экземпляров разных типов с одинаковыми именами *1025* в коллекции, которая использует внутренне hashCode (). . Общий эффект будет ограничен: если у вас n типов, у вас будет не более n коллизий из-за этого сценария. Другие факторы могут доминировать характеристики производительности.