我阅读了有关ConcurrentHashMap的JDK源代码。

但是以下代码使我感到困惑:

public boolean isEmpty() {
    final Segment<K,V>[] segments = this.segments;
    ...
}

我的问题是:

声明为“this.segments”:
final Segment<K,V>[] segments;

因此,这里在方法的开头,声明了相同的类型引用,指向了相同的内存。

作者为什么要这样写?他们为什么不直接使用this.segments?有什么原因吗?

最佳答案

这是涉及volatile变量的无锁代码的典型用法。在第一行中,您一次读取了volatile,然后使用它。同时,另一个线程可以更新volatile,但是您仅对最初读取的值感兴趣。

同样,即使所讨论的成员变量不是volatile,而是最终变量,该习惯用法也与CPU缓存有关,因为从堆栈位置进行读取比从随机堆位置进行读取更易于缓存。本地var最终绑定(bind)到CPU寄存器的机会也更高。

对于后一种情况,实际上存在一些争议,因为JIT编译器通常会解决这些问题,但是Doug Lea是坚持一般原则的人之一。

08-26 10:24