我正在阅读关于Java中的并发的官方Oracle文档,我想知道Collection返回的有什么区别
public static <T> Collection<T> synchronizedCollection(Collection<T> c);
Run Code Online (Sandbox Code Playgroud)
并使用例如a
ConcurrentHashMap.我假设我用synchronizedCollection(Collection<T> c)的是HashMap.我知道一般来说,同步集合本质上只是我的装饰器HashMap所以很明显a ConcurrentHashMap的内部结构有所不同.您是否有关于这些实施细节的信息?
编辑:我意识到源代码是公开的: ConcurrentHashMap.java
我一直在通读Concurency in PracticeBrian Goetz 的著作。
在关于 Lock Striping 的章节中写到ConcurrentHashMap使用 16 个存储桶来改进多个线程的多线程访问:
锁拆分有时可以扩展到对一组可变大小的独立对象进行分区锁定,在这种情况下,它被称为锁条带化。比如ConcurrentHashMap的实现使用了16个锁的数组,每个锁守护着1/16的hash桶;存储桶 N 由锁 N mod 16 保护。
我已经阅读了这些问题:
需要简单解释“锁条带化”如何与 ConcurrentHashMap 配合使用
但是,这些答案对 Java 版本 <= 7 有效。
对于 Java 8+,行为似乎发生了重大变化。对于 Java 8+,似乎不是为 Segment 而是为表 ( transient volatile ConcurrentHashMap.Node<K, V>[] table;) 中的特定节点获取锁。例如对于putVal操作:
ConcurrentHashMap.Node var7;
.... ///retrive node for var7
synchronized(var7) {
....
}
Run Code Online (Sandbox Code Playgroud)
并且从 Java8 + 字段 likeDEFAULT_CONCURRENCY_LEVEL和 classSegment似乎在实现中未使用(它仅用于私有方法中,writeObject::ObjectOutputStream并且在ConcurrentHashMap实现中的任何地方都不会调用此方法)。
ConcurrentHashMap实施中发生如此重大变化的原因是什么?
如果类Segment …