Der von hashCode()
zurückgegebene Wert ist keinesfalls garantiert die Speicheradresse des Objekts. Ich bin mir nicht sicher über die Implementierung in der Object
Klasse, aber bedenken Sie, dass die meisten Klassen hashCode()
überschreiben werden, so dass zwei Instanzen, die semantisch äquivalent sind (aber nicht dieselbe Instanz sind), auf denselben Wert hashen. Dies ist besonders wichtig, wenn die Klassen in einer anderen Datenstruktur verwendet werden können, z. B. Set, die darauf beruht, dass mit equals
übereinstimmt.
Es gibt keine hashCode()
, die eine Instanz eines Objekts eindeutig identifiziert, egal was passiert. Wenn Sie einen Hashcode verwenden möchten, der auf dem zugrunde liegenden Zeiger basiert (z. B. in der Sun-Implementierung), verwenden Sie . Dies wird an die Standardmethode hashCode
delegiert, unabhängig davon, ob sie überschrieben wurde.
Trotzdem kann sogar System.identityHashCode()
den gleichen Hash für mehrere Objekte zurückgeben. Sehen Sie die Kommentare für eine Erklärung, aber hier ist ein Beispielprogramm, das kontinuierlich Objekte erzeugt, bis es zwei mit dem gleichen System.identityHashCode()
findet. Wenn ich es ausführe, findet es schnell zwei System.identityHashCode()
s, die übereinstimmen, im Durchschnitt nach dem Hinzufügen von etwa 86.000 langen Wrapper-Objekten (und Integer-Wrapper für den Schlüssel) zu einer Karte.
public static void main(String[] args) {
Map<Integer,Long> map = new HashMap<>();
Random generator = new Random();
Collection<Integer> counts = new LinkedList<>();
Long object = generator.nextLong();
// We use the identityHashCode as the key into the map
// This makes it easier to check if any other objects
// have the same key.
int hash = System.identityHashCode(object);
while (!map.containsKey(hash)) {
map.put(hash, object);
object = generator.nextLong();
hash = System.identityHashCode(object);
}
System.out.println("Identical maps for size: " + map.size());
System.out.println("First object value: " + object);
System.out.println("Second object value: " + map.get(hash));
System.out.println("First object identityHash: " + System.identityHashCode(object));
System.out.println("Second object identityHash: " + System.identityHashCode(map.get(hash)));
}
Beispiel Ausgang:
Identical maps for size: 105822
First object value: 7446391633043190962
Second object value: -8143651927768852586
First object identityHash: 2134400190
Second object identityHash: 2134400190
einen besonderen Grund dies wurde modded nach unten? Wenn etwas hier falsch ist, würde ich eine Korrektur lieben, aber ohne Erklärung zu verwerfen, bringt nichts zur Diskussion. – danben
Vor ein paar Jahren erklärte Ted Neward in http://blogs.tedneward.com/2008/07/16/ObjecthashCode+Implementation.aspx wie die OpenJDK Object.hashCode() implementiert. Der OpenJDK leitet den Hash-Code von der Objektadresse ab, speichert diesen Wert jedoch im Cache und gibt ihn an nachfolgende Aufrufer zurück, falls sich das Objekt im Speicher bewegt und seine Adresse ändert. Nachdem ich kurz den neuesten Code gelesen habe, habe ich festgestellt, dass sich die Implementierung nicht geändert hat, seit Neward seinen Artikel geschrieben hat. –
Das scheint meine Antwort zu unterstützen. – danben