Как работает метод hashCode() java?

Мне любопытно, как java генерирует хэш-значения с помощью метода hashCode() API-интерфейса Object?

Ответ 1

Java не генерирует hashCode(), т.е. здесь ничего автоматического не происходит. Однако Object генерирует HashCode на основе адреса памяти экземпляра объекта. Большинство классов (особенно если вы собираетесь использовать их в любом из API Collection) должны реализовать свой собственный HashCode (и по контракту собственный метод equals).

Ответ 2

hashCode() Object на самом деле является нативным методом, и реализация на самом деле не является чистой Java. Теперь, в отношении того, как это работает, этот ответ от Tom Hawtin отлично справляется с объяснением:

Многие люди утверждают, что Object.hashCode вернет адрес представления объекта в памяти. В современных реализациях объекты фактически перемещаются в памяти. Вместо этого область заголовка объекта используется для хранения значения, которое может быть лениво выведено из адреса памяти в момент, когда сначала запрашивается значение.

Весь ответ на самом деле стоит прочитать.

Ответ 3

Согласно документации Java Platform API, вычисление hashcode основано на 32-битном внутреннем JVM-адресе Object.

Верно, что объект перемещается во время выполнения (AFAIK - единственная причина - сборщик мусора). Но hashcode не изменяется.

Итак, когда у вас есть такой объект

Person person1 = new Person();
person1.setName("Alex");

Person person2 = new Person();
person2.setName("Alex");

Person person3 = person2;

В этом случае person1.hashCode не будет равен person2.hashCode, потому что адреса памяти этих двух объектов не совпадают.

Но person2.hashCode будет равен person3, потому что они указывают на один и тот же объект.

Итак, если вам нужно использовать метод hashCode для ваших объектов, вы должны реализовать его самостоятельно.

Кстати, реализация String.hashCode отличается. Это примерно так: (синтаксис С#)

public int hashCode(String str)
{
  int h = 0;

  for (int i = 0; i < str.Length; i++)
    h = (h * 31) + str[i];

  return h;
}

edit: Здесь не выполняется проверка переполнения, поэтому hashCode может быть положительным или отрицательным.

Ответ 4

Object.hashCode() использует System.identityHashCode(), который основан на идентификационном номере для данного объекта.

Ответ 5

Java не создает значимого hashCode для вас, это ваша работа как программиста для создания полезного hashCode. Значение по умолчанию hashCode - это только расположение памяти.

Ответ 6

Функция HashCode() имеет несколько параметров для создания хэш-кода. Он устанавливает параметр запуска JVM. Функция, которая создает hashCode(), написанную на С++, и вы можете видеть код здесь

  • HashCode == 0: Просто возвращает случайные числа без отношения к тому, где в памяти объект найден. Насколько я могу разобраться, глобальные чтение-запись семян не оптимальна для систем с большим количеством процессоры.
  • HashCode == 1: Подсчитывает значения хеш-кода, не уверен, какое значение они начинаются, но это кажется довольно высоким.
  • HashCode == 2: Всегда возвращает тот же самый хэш-код идентификатора 1. Это можно использовать для проверки кода, который зависит от идентичности объекта. причина, по которой JavaChampionTest вернул URL Kirk в приведенном выше примере что все объекты возвращали один и тот же хэш-код.
  • HashCode == 3: Подсчитывает значения хэш-кода, начиная с нуля. Это не выглядит потокобезопасным, поэтому несколько потоков могут генерировать объекты с одинаковым хеш-кодом.
  • HashCode == 4:. Это, похоже, имеет некоторое отношение к местоположению памяти на котором был создан объект.
  • HashCode >= 5: Это алгоритм по умолчанию для Java 8 и имеет для каждой нити. В нем используется схема переноса x-shift Marsaglia для производства псевдослучайные числа.

Информация была взята из здесь