为什么在Java已经有ConcurrentHashMap的情况下,我们还需要Scala中的ParHashMap?

3

我考虑了两个类似的集合 - Scala的ParHashMap和Java的ConcurrentHashMap。它们都具有相同的时间复杂度,并且都是线程安全和无锁的,但它们在底层上基于不同的概念 - 分支和哈希表。这种推理引出了一个问题:既然有Java的ConcurrentHashMap,为什么还需要Scala的ParHashMap呢?


ConcurrentHashMap 不是无锁的。 - talex
@talex,您错了 - https://en.wikipedia.org/wiki/Java_ConcurrentMap#Lock-free_atomicity - pacman
@talex 我认为在Java 8之前它曾经不是无锁的,但现在已经改变了。 - Louis Wasserman
@ Louis Wasserman ConcurrentHashMap 始终是 "无锁" 的,但在 Java 7 中,它通过利用 "Lock stripping" 并发模式来使用一个 Node 结构。但在 Java 8 中,这种方法被禁用,并且在冲突的情况下将会建立 rb 树 - pacman
2
它提供了无锁查询、某些无锁更新操作以及不同键的并发更新。但是,在对同一键执行原子更新时,同步是不可避免的。 - Holger
显示剩余2条评论
1个回答

5

ConcurrentHashMap 是一个线程安全的 Map<> 实现。如果多个线程同时访问它,它们将保持同步。

ParHashMap 是一个并行集合。如果在此执行操作(如 map()filter()aggregate()),Scala 会自动为您并行化它(类似于 Spark,但仅在单个 JVM 内)。

总之,ConcurrentHashMap 提供了同步线程以实现并发的基本机制,ParHashMap 则同时处理了同步和执行。

编辑说明:请注意,ParHashMap 本身不一定是线程安全的。想法是从单个线程调用其方法,并让并行数据结构自己处理并行性。


是的,类似,但仅限于单个机器。您可以指定要使用的线程池。 - marios
1
实际上,Spark的发明者表示他在发明RDD抽象时从Scala的并行集合中获得了灵感。 - marios
2
我认为在Scala中实现线程安全的可变哈希映射的最佳选择是使用此处提供的实现:https://dev59.com/KWMm5IYBdhLWcg3whfae#17542165。即使您可以强制使用ParHashMap,但这并不是完成此任务的正确工具。 - marios
2
从Java 8开始,ConcurrentHashMap也支持几种并行处理方法,请参阅以forEach…reduce…search…开头的方法(或通常具有第一个参数long parallelismThreshold的所有方法)。 - Holger
1
我并没有说它是线程安全的。很可能不是。我认为你不会想从多个线程中调用它。这有点违背了初衷。 - marios
显示剩余8条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接