讲师中心 微信公众号
AI工具推荐 视频效率加速

并发多线程下的 ArrayList 数据丢失案例:通过源码分析由于 size++ 非原子操作产生的索引覆盖问题

千浩姑娘_7919

千浩姑娘_7919

发布时间:2026-05-01 09:18:17

|

962人浏览过

|

来源于php中文网

原创

ArrayList在多线程下非线程安全,核心在于add()中size++的非原子性(读-改-写三步分离),导致竞态覆盖与size少计;扩容时多线程各自复制数组并覆盖引用,加剧数据丢失;常见静默丢数而非抛ArrayIndexOutOfBoundsException。

并发多线程下的 arraylist 数据丢失案例:通过源码分析由于 size++ 非原子操作产生的索引覆盖问题

ArrayList 在多线程环境下不是线程安全的,核心问题出在 add() 方法中 size++ 操作的非原子性,导致多个线程同时扩容、写入时发生索引覆盖,最终出现数据丢失或数组越界等异常。

add() 方法的非原子三步操作

调用 add(E e) 时,实际执行三个分离步骤:

  • 检查容量是否足够(ensureCapacityInternal)——可能触发扩容
  • 将元素赋值到 elementData[size] 位置
  • 执行 size++(即 size = size + 1)

其中第2、3步看似连贯,但 size++ 是“读取-修改-写入”三阶段操作,在 JVM 层并非原子指令。当两个线程 T1、T2 同时执行到这一步,可能出现如下竞态:

  • T1 读取 size = 9
  • T2 也读取 size = 9
  • T1 计算 9+1=10,写回 size = 10,并把元素存入 elementData[9]
  • T2 同样计算 9+1=10,写回 size = 10,并把元素也存入 elementData[9]

结果:两个元素都写到了下标 9,前一个被覆盖;size 最终为 10(应为 11),逻辑长度少计 1。

扩容过程加剧竞争风险

当多个线程触发扩容(如初始容量为 0 或满载),会进入 grow() 方法重新分配数组并复制旧数据。此时若未同步:

  • 两个线程可能各自创建新数组,各自复制一次旧数据
  • 后完成的线程用新数组覆盖了 elementData 引用,导致先完成线程的复制结果丢失
  • 更严重的是:复制过程中 size 可能已被其他线程修改,造成复制数量不准(如复制了 9 个,但实际已有 10 个)

这种“复制-赋值”分离,叠加 size 状态不同步,使数据丢失从偶发变为高概率事件。

为什么不会抛 ArrayIndexOutOfBoundsException?

很多人误以为并发 add 会直接越界报错,其实不然:

  • 扩容判断基于旧 size 值,只要任一线程提前扩容成功,elementData 就已变长
  • 后续线程即使读到过期 size,写入的下标仍大概率在新数组范围内(如 size=9 写 elementData[9],而新数组长度已是 16)
  • 真正报错往往出现在极端情况:多个线程在无锁下反复扩容失败、size 错乱后,某次写入超出所有已知容量

所以生产环境更常见的是“静默丢失”——日志没报错,但业务数据莫名少了一条。

验证与替代方案

可通过循环启动 100 个线程,每个向同一 ArrayList 添加 1000 个不同元素,最终 size 很可能

安全替代方式包括:

  • Vector:add 方法加了 synchronized,但性能差、已不推荐
  • Collections.synchronizedList(new ArrayList()):手动同步,但仅方法级,遍历仍需额外同步块
  • CopyOnWriteArrayList:适合读多写少,写操作复制整个数组,无锁但内存和 CPU 开销大
  • 使用阻塞队列(如 LinkedBlockingQueue)或并发集合(ConcurrentHashMap 模拟列表语义)

热门AI工具

更多
讯飞绘文

讯飞绘文是一款由科大讯飞推出的一站式 AIGC 内容运营平台。

立刻MV
立刻MV Hot

立刻MV是一款AI文本写作工具,AI 音乐视频(MV)创作工具。

音述AI
音述AI Hot

一款AI音频处理工具,主要用于音述AI是一个以“用声音述说故事”为核心的 AI 音乐创作与声音分享社区,适合需要提升相关任务效率的用户。

AionClaw
AionClaw Hot

AionClaw是一款面向办公、创作和编程任务的AI桌面智能体。

WorkBuddy

一款AI办公效率工具,主要用于腾讯云推出的AI原生桌面智能体工作台,适合需要提升相关任务效率的用户。

DeepSeek

DeepSeek是一款面向对话、写作、编程和推理场景的AI大模型工具。

超级简历WonderCV

一款AI办公效率工具,主要用于免费求职简历模版下载制作,应届生职场人必备简历制作神器,适合需要提升相关任务效率的用户。

豆包大模型

豆包大模型是一款由字节跳动推出的企业级大语言模型服务平台。

切问学术

切问学术是一款AI论文写作工具,复旦大学NLP团队推出的AI学术智能体。

相关专题

更多
Python 多线程与异步编程实战
Python 多线程与异步编程实战

本专题系统讲解 Python 多线程与异步编程的核心概念与实战技巧,包括 threading 模块基础、线程同步机制、GIL 原理、asyncio 异步任务管理、协程与事件循环、任务调度与异常处理。通过实战示例,帮助学习者掌握 如何构建高性能、多任务并发的 Python 应用。

1049

2025.12.24

java多线程相关教程合集
java多线程相关教程合集

本专题整合了java多线程相关教程,阅读专题下面的文章了解更多详细内容。

363

2026.01.21

C++多线程相关合集
C++多线程相关合集

本专题整合了C++多线程相关教程,阅读专题下面的的文章了解更多详细内容。

519

2026.01.21

C# 多线程与异步编程
C# 多线程与异步编程

本专题深入讲解 C# 中多线程与异步编程的核心概念与实战技巧,包括线程池管理、Task 类的使用、async/await 异步编程模式、并发控制与线程同步、死锁与竞态条件的解决方案。通过实际项目,帮助开发者掌握 如何在 C# 中构建高并发、低延迟的异步系统,提升应用性能和响应速度。

369

2026.02.06

C++多线程并发控制与线程安全设计实践
C++多线程并发控制与线程安全设计实践

本专题围绕 C++ 在高性能系统开发中的并发控制技术展开,系统讲解多线程编程模型与线程安全设计方法。内容包括互斥锁、读写锁、条件变量、原子操作以及线程池实现机制,同时结合实际案例分析并发竞争、死锁避免与性能优化策略。通过实践讲解,帮助开发者掌握构建稳定高效并发系统的关键技术。

213

2026.03.16

Java 多线程与并发编程实战
Java 多线程与并发编程实战

深入讲解 Java 并发编程体系,涵盖 Thread / Runnable / Callable 线程创建方式、线程生命周期与状态转换、synchronized 同步锁与 Lock/ReentrantLock 显式锁、volatile 可见性保证、ThreadPool 线程池配置与调优(核心参数/拒绝策略)、JUC 并发工具类(CountDownLatch/CyclicBarrier/Semaphore/ConcurrentHashMa

309

2026.04.17

C++ 多线程使用教程大全
C++ 多线程使用教程大全

系统讲解 C++11 及后续标准引入的多线程编程能力,涵盖 std::thread 线程创建与生命周期管理、std::mutex / shared_mutex 互斥锁与读写锁、std::condition_variable 条件变量同步、std::atomic 原子操作与内存序(memory_order)、std::future / promise / async 异步任务、线程池的设计与实现、死锁检测与避免策略,帮助开发者编写正确高效

196

2026.04.28

Python多线程、多进程与并发编程教程大全
Python多线程、多进程与并发编程教程大全

系统讲解 Python 的并发与并行编程体系,涵盖 GIL 全局解释器锁的原理与影响分析、threading 模块的线程创建/锁/事件/信号量、multiprocessing 模块的进程创建/进程间通信(Queue/Pipe/共享内存)、concurrent.futures 线程池与进程池的统一接口、I/O 密集型与 CPU 密集型任务的方案选择、多线程竞态条件排查与线程安全数据结构、subprocess 子进程管理,帮助开发者根据任务

174

2026.05.08

LLVM自定义Pass怎么写
LLVM自定义Pass怎么写

本专题聚焦LLVM自定义Pass开发,整理Pass类结构、run()方法、PreservedAnalyses、CMake构建、插件注册、-load-pass-plugin加载和测试用例编写流程。

40

2026.09.30

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
热门推荐
/
最新课程
关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn