CopyOnWriteArrayList 通过写时复制(Copy-On-Write)机制实现线程安全,具体方式如下:

写时复制机制

  • 读操作:直接读取当前数组,无需加锁,因此多个线程可以并发读取;

  • 写操作:每次修改时,先复制当前数组,修改副本后再替换原数组。这个过程需要加锁,确保只有一个线程进行写操作;

  • CopyOnWriteArrayList 中,写操作加锁不会阻塞读操作。这是它的一个重要特性,也是它能够高效支持并发读操作的关键原因。

写复制的特性

  • 读操作无锁

    • 读操作直接访问当前数组,不需要加锁,因此不会被写操作的锁阻塞;

    • 由于数组是不可变的(写操作会创建新数组),读操作可以安全地并发进行。

  • 写操作加锁

    • 写操作(如 addsetremove)会加锁,但锁的范围仅限于写操作本身;

    • 写操作会复制当前数组,修改副本,然后用新数组替换原数组。这个过程是线程安全的,因为只有一个线程可以持有锁。

  • 读写分离

    • 写操作修改的是数组的副本,而读操作始终访问原数组或新数组,两者互不干扰;

    • 替换数组的操作是原子性的(通过 volatile 变量保证可见性),因此读操作要么看到旧数组,要么看到新数组,不会看到中间状态。