答案 0 :(得分:0)
ConcurrentHashMap.iterator()不保证您迭代时会或不会看到添加的条目。有一个内部订单,它会跳过条目,如果在该点之前添加,则看不到该条目。
如果再次遍历值,则应该在第二个中看到它是在第一个条目之前。
答案 1 :(得分:0)
您使用ConsurrentHashMap
而不是像Map
这样的常规HashMap
实现可能是有原因的。如果尝试使用其中一种实现并运行代码,您会注意到ConcurrentModificationException
,在迭代过程中更新HashMap
时,可能会抛出该ConcurrentHashMap
。如果您将该实现更改为Map
,则会更改以下内容:
一个哈希表,它支持检索的完全并发性和更新的高期望并发性。 [...]检索操作(包括get)通常不会阻塞,因此可能与更新操作(包括put和remove)重叠。检索反映了发生后最新完成的更新操作的结果。
因此,在迭代Map
时允许并发更新。现在,您是否可以实际看到该值的问题与Map
实现的迭代顺序有关(该实现可以在Java版本之间更改,因为通常没有迭代顺序)在Map
中)。如果在当前迭代之前插入了元素,则不会对其进行迭代。如果在此之后插入元素,它将在控制台上打印出来。毕竟,您不应该依赖它。
但是,如果您再次遍历Iterator<String> it = map.keySet().iterator();
while (it.hasNext()) {
System.out.println(map.get(it.next()));
}
iPhone
HTC one
S5
Xperia Z <<< here it is
iPhone
HTC one
S5
您将在输出中正确看到该值:
double 24.9
现在可以证明先前的假设是正确的,因为键“ Sony”已经被首先迭代,因此它不会出现在先前的迭代中。如果您将其与第一次尝试进行比较,则最后一次迭代了键“ d”,因此它会显示在控制台上。确切地说,如果您迭代了一个值而不是第一个值,那么它将显示出来(因为您已经在第二次迭代中添加了它)。
但是,请记住,如前所述,迭代顺序可能会在Java版本之间发生变化,并且这仅适用于您的具体示例。