不同哈希码的结果,但两个 java 对象相同
Consequences of different hashcodes but same equals for two java objects
我知道我们应该有相同的 hashcodes
incase equals
对于两个 java 对象是相同的,但只是想了解如果 hashcodes
不相同但是 equals
returns true
,对于像 HashMap、HashSet 等集合,会有什么后果
它只会影响性能还是会影响这些集合 类 的 behavior/functionality。
它会破坏功能。如果您要在散列映射或散列集中查找对象,它会使用散列码来找到它。如果hash code不一致,很可能找不到。
哈希码最基本的要求是两个相等的对象必须具有相同的哈希码。其他都是次要的。
后果将是意想不到的行为。
如果 a.equals(b) == true
但 a.hashCode()!=b.hashCode()
,set.add(a)
后跟 set.contains(b)
很可能 return false
(假设 set
是 HashSet
),尽管根据 equals
它应该 return true
。 (最有可能但不确定的原因是两个不同的哈希码仍然有机会映射到 HashSet/HashMap
的同一个桶,在这种情况下你仍然可以获得 true
)。
如果两个对象相等,它们的哈希码将始终return相同的值。
请注意,每当重写此方法时,通常都需要重写 hashCode 方法,以维护 hashCode 方法的一般约定,即相等的对象必须具有相等的哈希码。
请阅读this
我们将对象称为 o1
和 o2
,其中 o1.equals(o2)
但 o1.hashCode() != o2.hashCode()
考虑以下几点:
Map map = new HashMap();
Set set = new HashSet();
map.put(o1, "foo");
set.add(o1);
以下断言将失败
Assert.assertTrue(map.containsKey(o2));
Assert.assertTrue(set.contains(o2));
它会在获取过程中错过桶。 HashMap 旨在存储大量数据,在最佳情况下获取时间为 O(1)。为此,它存储针对哈希码(我们通常称为桶)标记的 key/values。这称为散列技术。
因此,您将它存储在哈希图中,哈希码编号为 100,现在您正尝试使用不同的哈希码(比如 200)获取对象(即在不同的存储桶中查找)。因此,即使您的对象在 hashmap 中,它也无法检索它,因为它会尝试在不同的存储桶(即 200)中查找。
这就是我们应该有相同哈希码的原因,因为两个 java 对象
相等
HashMap/HashSet 是为了帮助您找到集合中的目标对象。如果两个相等的对象具有不同的哈希码,则您不太可能在哈希桶中找到该对象。
我知道我们应该有相同的 hashcodes
incase equals
对于两个 java 对象是相同的,但只是想了解如果 hashcodes
不相同但是 equals
returns true
,对于像 HashMap、HashSet 等集合,会有什么后果
它只会影响性能还是会影响这些集合 类 的 behavior/functionality。
它会破坏功能。如果您要在散列映射或散列集中查找对象,它会使用散列码来找到它。如果hash code不一致,很可能找不到。
哈希码最基本的要求是两个相等的对象必须具有相同的哈希码。其他都是次要的。
后果将是意想不到的行为。
如果 a.equals(b) == true
但 a.hashCode()!=b.hashCode()
,set.add(a)
后跟 set.contains(b)
很可能 return false
(假设 set
是 HashSet
),尽管根据 equals
它应该 return true
。 (最有可能但不确定的原因是两个不同的哈希码仍然有机会映射到 HashSet/HashMap
的同一个桶,在这种情况下你仍然可以获得 true
)。
如果两个对象相等,它们的哈希码将始终return相同的值。
请注意,每当重写此方法时,通常都需要重写 hashCode 方法,以维护 hashCode 方法的一般约定,即相等的对象必须具有相等的哈希码。
请阅读this
我们将对象称为 o1
和 o2
,其中 o1.equals(o2)
但 o1.hashCode() != o2.hashCode()
考虑以下几点:
Map map = new HashMap();
Set set = new HashSet();
map.put(o1, "foo");
set.add(o1);
以下断言将失败
Assert.assertTrue(map.containsKey(o2));
Assert.assertTrue(set.contains(o2));
它会在获取过程中错过桶。 HashMap 旨在存储大量数据,在最佳情况下获取时间为 O(1)。为此,它存储针对哈希码(我们通常称为桶)标记的 key/values。这称为散列技术。 因此,您将它存储在哈希图中,哈希码编号为 100,现在您正尝试使用不同的哈希码(比如 200)获取对象(即在不同的存储桶中查找)。因此,即使您的对象在 hashmap 中,它也无法检索它,因为它会尝试在不同的存储桶(即 200)中查找。 这就是我们应该有相同哈希码的原因,因为两个 java 对象
相等HashMap/HashSet 是为了帮助您找到集合中的目标对象。如果两个相等的对象具有不同的哈希码,则您不太可能在哈希桶中找到该对象。