简体   繁体   English

相等的对象必须具有相等的哈希码?

[英]Equal Objects must have equal hashcodes?

Equal Objects must have equal hashcodes. 相等的对象必须具有相等的哈希码。 As per my understanding this statement is valid when we have intention of using object in hashbased datastuctures. 根据我的理解,当我们打算在基于哈希的数据结构中使用对象时,此语句是有效的。 This is one of contract for hashcode and equals method in java docs. 这是Java文档中哈希码和equals方法的合同之一。 I explored the reason why this is said and looked in the implementation of hashtable and found out below code in put method 我探讨了为什么要这样说,并查看了hashtable实现,并在put方法中找到了以下代码

if ((e.hash == hash) && e.key.equals(key)) 

So I got it, contract came from condition e.hash == hash above. 所以我明白了,合同来自上面的条件e.hash == hash I further tried to explore why java is checking hashcode when comparing two objects for equality. 我进一步尝试探索为什么在比较两个对象是否相等时java是否检查哈希码。 So here is my understaing 所以这是我的底线

  • If two equal object have equal hascodes then they can be stored in the same bucket and this will be good in terms of look up in single bucket only 如果两个相等的对象具有相等的hascode,则可以将它们存储在同一存储桶中,这对于仅在单个存储桶中查找而言将是一个好习惯

  • Its better to check hashcode then actually calling equals method because hascode method is less costly than equals method, because here we just have to compare int value where in equals method may be invloving object field comparison. 最好检查哈希码,然后再实际调用equals方法,因为hascode方法的成本比equals方法便宜,因为在这里,我们只需要比较int值(其中equals方法可能涉及对象字段比较)。 So hashcode method providing one extra filter. 因此,哈希码方法提供了一个额外的过滤器。

Please correct me if both above reasons are valid? 如果以上两个原因均正确,请纠正我?

  1. Correct, just a small correction - if two unequal objects have the same hashcode. 正确,只需进行少量校正-如果两个不相等的对象具有相同的哈希码。
  2. Not exactly, It's better to check it first, as a filter for the non-equal, but if you want to make sure the objects are equal, you should call equals() 不完全是,最好先检查一下,作为不等式的过滤器,但是如果要确保对象相等,则应调用equals()

You got it wrong. 你理解错了。 equals just returns a boolean value (two possible values), and needs another object to compare against. equals仅返回一个布尔值(两个可能的值),并且需要另一个对象进行比较。 hashCode returns an int (2^32 possible values), and only needs the object to be called. hashCode返回一个int(2 ^ 32个可能的值),并且只需要调用该对象。

The HashMap tries to distribute all the objects it holds among buckets. HashMap尝试将其持有的所有对象分布在各个存储桶中。 When put is called on the map, it has to decide which bucket it will use for the given object. 在地图上调用put ,它必须确定将用于给定对象的存储桶。 It thus uses hashCode (modulo the number of buckets) to decide which bucket to use. 因此,它使用hashCode (对存储桶数取模)来决定使用哪个存储桶。 Then, once the bucket is found, it has to check whether the key is already in the map or not. 然后,一旦找到存储桶,它就必须检查密钥是否已在地图中。 To do this, it compares every object in the bucket with the object to put in the map. 为此,它将存储桶中的每个对象与要放入地图中的对象进行比较。 And to do this, it uses equals . 为此,它使用equals If the object isn't found, it adds it in the bucket. 如果找不到该对象,则将其添加到存储桶中。

hashCode isn't used because it's faster than equals . 不使用hashCode因为它比equals更快。 It's used because it allows distributing keys among a set of buckets. 之所以使用它,是因为它允许在一组存储桶之间分配密钥。 And it's much faster to compute the hashCode once and compare the object with (hopefully) 0, one or two objects in the same bucket that to compare the object with the thousands of objects already stored in the map. 而且,一次计算hashCode并将对象与(希望)0(在同一存储桶中的一个或两个对象)进行比较的速度要快得多,以将对象与已存储在地图中的数千个对象进行比较。

" I further tried to Exlpore why java is checking Hashcode when comparing two objects for equality". “我进一步尝试向Exlpore解释为什么在比较两个对象是否相等时java是否要检查Hashcode”。 Put method is not just checking for equality, it is trying to first narrow down the bucket and then use the equals. Put方法不仅检查相等性,还尝试首先缩小范围,然后使用均等值。 That is why we need to combine HashCode with Equals in case of bucketed collections. 这就是为什么我们需要将HashCode与Equals结合使用的原因,以防出现分类收集。

But if your sole intention is to just check equality between two objects, you will never need a hashcode method. 但是,如果您唯一的目的只是检查两个对象之间的相等性,则永远不需要哈希码方法。

Obj1.equals(Obj2) will never use the hashcode method by default. 默认情况下,Obj1.equals(Obj2)永远不会使用哈希码方法。

Its a general type of contract so that when we store the objects inside a hashing based data structure, then we should always consistently put or get the same object to and from the hashtable. 它是一种普通的合同类型,因此当我们将对象存储在基于哈希的数据结构中时,我们应该始终一致地将相同的对象放入哈希表或从哈希表中获取相同的对象。 Its a contract which we have created to be followed such that the entry/put processes occur smoothly. 它是我们创建的合同,必须遵循,以便顺利进行输入/输出过程。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM