Java面试必备:Java线程安全的集合详解
Java并发面试题 - Java线程安全的集合有哪些?
一、线程安全集合概述
在Java多线程编程中,当多个线程同时访问和修改同一个集合时,可能会引发数据不一致的问题。为了解决这个问题,Java提供了多种线程安全的集合实现。
二、传统线程安全集合
1. Vector和Hashtable
Java早期提供的线程安全集合,通过synchronized关键字实现同步。
Vector
vector.add("item1");
vector.add("item2");
Hashtable
hashtable.put(1, "value1");
2. Collections工具类包装的集合
通过Collections.synchronizedXXX()方法可以将非线程安全集合包装成线程安全版本。
List
Map
Set
三、JUC并发集合
Java 5引入了java.util.concurrent包,提供了更高效的并发集合实现。
1. CopyOnWriteArrayList
写时复制的List实现,适合读多写少的场景。
CopyOnWriteArrayList
cowList.add("item1");
String item = cowList.get(0);
2. ConcurrentHashMap
高并发的HashMap实现,采用分段锁技术(Java 7)或CAS+synchronized(Java 8+)。
ConcurrentHashMap
concurrentMap.put(1, "value1");
String value = concurrentMap.get(1);
3. ConcurrentLinkedQueue
基于链接节点的无界线程安全队列,采用CAS实现。
ConcurrentLinkedQueue
queue.offer("item1");
String item = queue.poll();
4. BlockingQueue接口实现
阻塞队列,常用于生产者-消费者模式。
BlockingQueue
// 生产者
blockingQueue.put("item1");
// 消费者
String item = blockingQueue.take();
四、线程安全集合对比
集合类型实现方式适用场景特点Vector/Hashtable方法级synchronized遗留系统全表锁,性能差Collections.synchronizedXXX方法级synchronized简单同步需求包装器模式,性能一般CopyOnWriteArrayList写时复制读多写少读无锁,写复制开销大ConcurrentHashMap分段锁/CAS高并发Map并发度高,性能好ConcurrentLinkedQueueCAS高并发队列无锁,非阻塞BlockingQueue锁+条件变量生产者-消费者阻塞操作,容量控制五、选择建议
读多写少:考虑CopyOnWriteArrayList高并发Map:优先选择ConcurrentHashMap生产者-消费者:使用BlockingQueue实现类简单同步:可以使用Collections.synchronizedXXX包装避免使用:Vector和Hashtable(遗留类)
六、总结
Java提供了丰富的线程安全集合选择,从早期的synchronized集合到现代的并发集合,开发者应根据具体场景选择最合适的实现。理解各种线程安全集合的内部实现机制,有助于编写出更高效、更可靠的多线程程序。