java hashtable包含奇怪
在什么情况下给出了hashCode和equals()的正确实现,下面的代码可以返回false吗?java hashtable包含奇怪
myLinkedHashMap.containsKey(myLinkedHashMap.keySet().iterator().next())
我可以想到的最可能的情况是即使hashCode
是“确定性”,它可能基于可变字段。如果您在Map
中更改用于计算hashCode
的字段,那么您将无法再找到它。
编辑:应澄清你'通常'将无法找到它了。偶尔它仍然可以工作,因为两个数字仍然可以重新进入同一个桶。当然,这只会增加混乱发生!
是的,突变。谢谢。 – 2012-03-22 21:40:20
目前尚不清楚你所说的“确定性”,但任何哈希变化的突变的关键是什么意思,它已经插入到哈希表后很容易有这种效果。
import java.util.*;
public class Test {
public static void main(String[] args) {
List<String> strings = new ArrayList<String>();
Map<List<String>, String> map = new LinkedHashMap<List<String>, String>();
map.put(strings, "");
System.out.println(map.containsKey(map.keySet().iterator().next())); // true
strings.add("Foo");
System.out.println(map.containsKey(map.keySet().iterator().next())); // false
}
}
的ArrayList<T>
哈希码是确定的,但是,这并不意味着它不会改变,如果列表中的内容发生变化。
如果您的hashCode
和equals
彼此不同意,则可能返回错误。例如,如果equals
方法总是返回false
,则这将返回false
,因为没有任何对象与映射中的键相等。
希望这会有所帮助!
如果
hashCode()
是基于是可变和这些属性在插入后改变实例属性,迭代过程中hashCode()
调用将返回不同的东西。equals()
应该基于这些相同的属性,它也会失败。当另一个线程已经删除了所有下一个在迭代中间的
Map
项目,将有没有更多的next()
。
我不会使用hashCode()
值作为键,我会把你自己的对象。
没有线程。 – 2012-03-22 21:31:22
并不重要,如果你正在考虑的特定实例不使用一个线程,你的**问题**问什么时候会发生,这是可能发生的一种情况。 – 2012-03-22 21:35:13
您可能需要先检查hasNext()。
不,它在那里。绝对有元素。 – 2012-03-22 21:32:13
我看到的每个散列算法都是“确定性”的,因为对于给定的一组输入值,您可以得到相同的散列值。
如果根据对象的可变属性计算哈希代码,则哈希代码在哈希映射后会发生变化,如果这些可变属性中的任何一个发生更改。
您可以在获取第一个键和调用containsKey之间删除另一个线程中的第一个键。
“确定性”是否指“正确”? – 2012-03-22 21:29:00
它在这种情况下并不重要,因为它是同一个对象,对吧?所以只要对同一个对象的2次调用产生相同的hashCode,就应该返回true。但是,是的,这也是正确的。 – 2012-03-22 21:30:01
但“确定性”并不意味着“对同一对象的2个调用产生相同的hashCode”。关于'ArrayList .hashCode'没有任何*非确定性的*,但看到我的答案... –
2012-03-22 21:34:44