Je crois comprendre que deux objets inégaux peuvent avoir le même hashcode. Comment cela serait-il géré lors de l'ajout ou de la récupération d'un fichier java HashMap?
Ils seront simplement ajoutés au même compartiment et equals()
sera utilisé pour les distinguer. Chaque compartiment peut contenir une liste d'objets avec le même code de hachage.
En théorie, vous pouvez renvoyer le même entier qu'un code de hachage pour n'importe quel objet d'une classe donnée, mais cela signifierait que vous perdriez tous les avantages en termes de performances de la carte de hachage et, en fait, stockerait les objets dans une liste.
Dans HashMap, les clés et leurs valeurs associatives sont stockées dans un nœud de liste lié dans le compartiment et les clés sont essentiellement comparées dans hashmap à l'aide de la méthode equals () et non par hashcode.
hm.put("a","aValue"); // Suppose hashcode created for key "a" is 209
hm.put("b","bValue"); // Here hashcode created for key "b" is 209 as well.
a.equals(b)
renvoie true
, bValue
remplacera aValue
et bValue
sera renvoyé.a.equals(b)
renvoie false
, un autre nœud sera créé dans la liste des compartiments. Ainsi, lorsque vous appelez get("b")
, vous obtiendrez bValue
puisque a.equals(b)
est false
.HashMap travaille sur le concept de hachage et d'indexation. En interne, HashMap stocke les valeurs dans Array of Nodes. Chaque nœud se comporte comme une liste liée.
Chaque nœud de la liste liée a 4 valeurs:
int hash
K key
V value
Node<K, V> next
HashMap structure interne:
Lors de l'insertion de la valeur dans HashMap, le premier hashcode de Key est généré et basé sur un algorithme, il calcule l'index.
Ainsi, notre valeur sera stockée dans un index spécifique avec hashcode, clé, valeur et adresse de l'élément suivant.
Lors de la récupération de la valeur depuis HashMap, le premier hashcode sera généré puis indexé (de la même manière qu'au moment de l'insertion). Tout en récupérant la valeur de index, il vérifie d’abord le hashcode; si hashcode correspond, il vérifie uniquement la clé de Node en utilisant la méthode equals. Si key correspond, alors seul valeur ou bien il recherchera le prochain nœud avec le même hashcode.
Dans ce cas, vous pouvez utiliser IdentityHashMap, où différents objets avec le même hachage sont considérés comme différents en fonction de leur identité.
Lorsque deux objets inégaux ont la même valeur de hachage, cela provoque une collision dans la table de hachage, car les deux objets veulent être dans le même emplacement (parfois appelé compartiment). L'algorithme de hachage doit résoudre de telles collisions. En revenant dans les mémoires de mon cours d'algorithme universitaire, je me souviens de trois façons de faire:
Je pense que les classes de hachage Java utilisent la troisième méthode, mais elles pourraient utiliser une approche combinée. La clé du bon hachage consiste toutefois à s’assurer que la table de hachage a une capacité suffisante et à écrire de bonnes fonctions de hachage. Une table de hachage comportant uniquement autant de compartiments que d'objets qu'elle contient aura probablement des conflits. Généralement, vous voulez que la table de hachage soit environ deux fois plus grande que le nombre d'objets qu'elle stocke. HashMap de Java augmentera au besoin, mais vous pouvez lui attribuer une capacité de départ et un facteur de charge si vous le souhaitez.
La fonction de hachage appartient au programmeur. Vous pouvez simplement renvoyer 0 pour tous les objets, mais cela signifiera que le hachage (à la fois le stockage et la récupération) deviendra O(n) au lieu de O(1) ... ou dans conditions générales, ce sera un chien lent.
Référence: http://www.coderanch.com/t/540275/Java/java/objects-hashcode-HashMap-retrieve-objects