Java HashMap密钥问题



我目前正在制作一个自定义序列化程序,作为项目的一部分,这里我也需要序列化引用,这意味着如果两个字段在序列化之前引用同一个项目,那么在反序列化之后也应该引用。

为此,我使用了一个HashMap,将每个对象映射到一个ID,我可以将该ID用作每个序列化对象的属性,同时跟踪哪些对象已经被序列化。不过我偶然发现了一些问题。

java HashMap似乎只检查键上的相等性,而不检查它们是否是相同的引用。例如,在下面的例子中,变量b最终为true:

HashMap<Object, Integer> map = new HashMap<Object, Integer>();
LinkedList<Object> ll1 = new LinkedList<Object>();
LinkedList<Object> ll2 = new LinkedList<Object>();
map.put(ll1, 5);
boolean b = map.containsKey(ll2);

有时,结果根本没有意义。这里,b也是真的:

HashMap<Object, Integer> map = new HashMap<Object, Integer>();
LinkedList<Object> ll1 = new LinkedList<Object>();
Stack<Object> stack = new Stack<Object>();
map.put(ll1, 5);
boolean b = map.containsKey(stack);

我想要的是ContainsKey方法不仅调用equals方法,还使用"=="-运算符检查引用是否相同。我能做到这一点而不需要查看整个密钥集吗?

提前感谢

Map接口的一般约定是,如果两个键都为null,或者它们不为null且为a.equals(b),则认为它们相等。它不使用==进行比较,除非键类的equals方法实现可以这样做。

LinkedListStack对象相等的原因是它们都实现了List接口,而List.equals的定义是,如果两个列表具有相同的大小,并且按相同的顺序包含相同的对象,则它们是相等的。因为它们都是空的,所以它们是"相等的"。

我相信你在找IdentityHashMap。只使用==而不使用Object.equals()来比较对象,这故意违反了Map接口的约定。同样,对于哈希代码,它使用System.identityHashCode,而不是任何重写的Object.hashCode()

最新更新