我需要创建一个对象集合。重点是我不想基于对象的 hashCode 和 equals 实现来进行哈希或相等性比较。相反,我希望哈希码和相等性仅基于每个对象的引用标识(即引用指针的值)。
我不确定如何在Java中实现这一点。
这样做的原因是我的对象没有可靠地实现 equals 或 hashCode,而在这种情况下,引用标识已经足够了。
我需要创建一个对象集合。重点是我不想基于对象的 hashCode 和 equals 实现来进行哈希或相等性比较。相反,我希望哈希码和相等性仅基于每个对象的引用标识(即引用指针的值)。
我不确定如何在Java中实现这一点。
这样做的原因是我的对象没有可靠地实现 equals 或 hashCode,而在这种情况下,引用标识已经足够了。
java.util.IdentityHashMap
(请注意,没有IdentityHashSet
)。查阅API文档可以了解更多信息:Map
接口,当比较键(和值)时使用引用相等代替对象相等。换句话说,在IdentityHashMap
中,仅当(k1==k2)
时,两个键k1
和k2
才被认为是相等的。(在正常的Map
实现(如HashMap
)中,仅当(k1==null ? k2==null : k1.equals(k2))
时,两个键k1
和k2
被认为是相等的。)Map
实现!虽然这个类实现了Map
接口,但它有意违反了Map
的一般约定,这个约定规定在比较对象时必须使用equals
方法。这个类只适用于极少数需要引用相等语义的情况。
编辑:请参见Joachim Sauer下面的评论,很容易基于某个Map
创建一个Set
。你需要这样做:Set<E> mySet = Collections.newSetFromMap(new IdentityHashMap<E, Boolean>());
hashcode
和equals
方法。Object[]
。这样做很丑陋,但是可行。 - polygenelubricantsObject
的equals
和hashCode
,并且已经有了get
和set
,使它成为在这种情况下工作的包装器。我们实际上不需要它的原子性特性,但也不会有什么坏处。它可能仍然被视为滥用库类,但它不像使用new Object[1]
数组那样丑陋。 - polygenelubricantsObject[]
是行不通的:假设你想在普通的 Set
中使用它们,那么 new Object[] {obj}.equals(new Object[] {obj})
的结果是 false
。 - Marcono1234你可以扩展HashSet
(或者实际上是AbstractSet
),并使用{{link1:IdentityHashMap
}}作为其支持,该映射使用{{link2:System.identityHashCode(object)
}}而不是obj.hashCode()
。
你可以简单地搜索IdentityHashSet
,已经有一些实现了。或者像Joachim Sauer建议的那样使用Collections.newSetFromMap(..)
。
当然,只有在你没有“拥有”对象类的情况下才应该这样做。否则,只需修复它们的hashCode()
即可。
hashCode()
比扩展HashSet
更容易。 - danbenhashCode()
。 - Bozho
newSetFromMap
:http://java.sun.com/javase/6/docs/api/java/util/Collections.html#newSetFromMap(java.util.Map%29 - Joachim Sauerjava.util.HashSet
的源代码(可以在JDK安装目录下的src.zip文件中找到),你会发现它在内部使用了一个HashMap
(正如Stephen C所说,它是基于HashMap
实现的)。 - Jesper