Java HashMap 默认不同步。
如果我们在多个线程添加和删除键值对的并发应用程序中从 HashMap 添加/删除键值对,我们最终可能会导致映射状态不一致。
同步HashMap - ConcurrentHashMap
如果我们希望在并发环境中使用 Map,我们的首选应该始终是使用 ConcurrentHashMap
类。ConcurrentHashMap
通过设计支持并发访问它的键值对。
我们不需要执行任何另外的代码修改来启用地图同步。
请注意,从 ConcurrentHashMap
获得的迭代器不会抛出 ConcurrentModificationException
。
然而,迭代器被设计为一次只能被一个线程使用。
这意味着我们从 ConcurrentHashMap 获得的每个迭代器都设计为由单个线程使用,不应传递。
如果我们这样做,则不能保证一个线程会看到另一个线程执行的映射更改(无需从映射中获取新的迭代器)。
迭代器保证在创建时反映地图的状态。
示例:
import java.util.Iterator; import java.util.concurrent.ConcurrentHashMap; public class HashMapExample { public static void main(String[] args) throws CloneNotSupportedException { ConcurrentHashMap<Integer, String> concurrHashMap = new ConcurrentHashMap<>(); //Put require no synchronization concurrHashMap.put(1, "A"); concurrHashMap.put(2, "B"); //Get require no synchronization concurrHashMap.get(1); Iterator<Integer> itr = concurrHashMap.keySet().iterator(); //Using synchronized block is advisable synchronized (concurrHashMap) { while(itr.hasNext()) { System.out.println(concurrHashMap.get(itr.next())); } } } }
输出:
A B
同步HashMap - Collections.synchronizedMap()
Synchronized HashMap 的工作方式也与 ConcurrentHashMap 非常相似,但几乎没有区别。
SynchronizedHashMap
一次只允许一个线程执行读/写操作,因为它的所有方法都声明为 synchronized 。ConcurrentHashMap
允许多个线程在映射中的不同段上独立工作。
这允许 ConcurrentHashMap 中更高程度的并发,从而提高整个应用程序的性能。
两个类的迭代器都应该在synchronized
块中使用,但是来自 SynchronizedHashMap 的迭代器是快速失败的。
ConcurrentHashMap 迭代器不是快速失败的。
import java.util.Collections; import java.util.HashMap; import java.util.Iterator; import java.util.Map; public class HashMapExample { public static void main(String[] args) throws CloneNotSupportedException { Map<Integer, String> syncHashMap = Collections.synchronizedMap(new HashMap<>()); //Put require no synchronization syncHashMap.put(1, "A"); syncHashMap.put(2, "B"); //Get require no synchronization syncHashMap.get(1); Iterator<Integer> itr = syncHashMap.keySet().iterator(); //Using synchronized block is advisable synchronized (syncHashMap) { while(itr.hasNext()) { System.out.println(syncHashMap.get(itr.next())); } } } }
输出:
A B