首页
学习
活动
专区
圈层
工具
发布
社区首页 >专栏 >在 Java 中,实现线程安全的 List 主要有三种常见方案

在 Java 中,实现线程安全的 List 主要有三种常见方案

原创
作者头像
学习........
发布2026-04-26 15:30:27
发布2026-04-26 15:30:27
200
举报

1. Vector(JDK 1.0 的远古遗迹)

这是 Java 最早提供的线程安全集合,现已基本被淘汰。

  • 底层实现: 内部通过动态数组(类似 ArrayList)存储数据。
  • 并发机制: 方法级别的重量级锁。它直接在所有的增删改查方法(如 add, get, size 等)上加上了 synchronized 关键字。
  • 致命缺点: 锁的粒度极大。无论读写,都会锁住整个当前实例对象(this)。在多线程高并发环境下,这会导致严重的锁竞争和上下文切换,性能极差。

2. Collections.synchronizedList(装饰器模式的折中方案)

通过 Collections.synchronizedList(new ArrayList<>()) 生成的包装类。

  • 底层实现: 采用装饰器模式(Decorator),内部持有一个普通的 List(如 ArrayList)和一个对象锁(mutex)。
  • 并发机制: 代码块级别的同步锁。它的所有操作方法内部都是一个 synchronized (mutex) 代码块。如果不显式指定 mutex,默认锁住的就是包装类对象本身。
  • 性能评估: 性能比 Vector 稍微好一点点(因为锁的是代码块而不是整个方法,且没有引入废弃的老旧 API),但本质依然是互斥锁(排他锁),读读操作依然互斥,无法满足高并发下的读性能要求。
  • 🚨 易错点(面试高频坑): 当你使用 Iterator 遍历这个安全的 List 时,必须在外部手动加锁。因为它的 iterator() 方法本身没有加锁,如果在遍历过程中其他线程修改了结构,依然会抛出 ConcurrentModificationException (快速失败机制 fail-fast)。

3. CopyOnWriteArrayList(JUC 包下的现代工业标准)

这是 java.util.concurrent 包下专为**“读多写少”**场景量身定制的并发安全 List。

  • 底层实现: 内部维护一个被 volatile 修饰的数组引用(private transient volatile Object[] array;),保证了数组指针修改时的内存可见性。
  • 并发机制(写操作): Copy-On-Write(写时复制) + 独占锁
    • 当执行 addset 等写操作时,它不会直接修改原数组,而是先获取锁(JDK 8 中是 ReentrantLock,JDK 11+ 优化为了更轻量的 synchronized)。
    • 然后,申请一块新内存,将原数组的数据全量拷贝一份出来。
    • 在新副本当中完成修改操作。
    • 最后,将内部的 volatile array 指针指向这个全新的数组,并释放锁。
  • 并发机制(读操作): 绝对的无锁化(Lock-Free)
    • 读操作直接读取当前的 array 引用指向的数组。因为写操作是在副本上进行的,绝不会对当前读线程产生干扰。
  • 优缺点:
    • 优: 读性能直接拉满,不会引发并发修改异常(采用弱一致性的 fail-safe 迭代器)。
    • 缺: 内存开销巨大(每次写都伴随着全量数组拷贝);数据最终一致性(读线程在数组指针切换前,读到的依然是老数据,不适合对数据实时性要求极高的场景)。

🌟 总结与技术选型对照表

方案

底层核心机制

读操作是否加锁

迭代器机制

适用场景

Vector

synchronized 方法

是(互斥锁)

Fail-Fast

已淘汰,遗留系统维护

SynchronizedList

synchronized 代码块

是(互斥锁)

Fail-Fast (需外部手动加锁)

简单的低并发同步场景

CopyOnWriteArrayList

独占锁 + 数组拷贝 + volatile

否(完全无锁)

Fail-Safe (快照机制)

读多写少、容忍最终一致性

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 1. Vector(JDK 1.0 的远古遗迹)
  • 2. Collections.synchronizedList(装饰器模式的折中方案)
  • 3. CopyOnWriteArrayList(JUC 包下的现代工业标准)
  • 🌟 总结与技术选型对照表
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档