的实现方法 "> 的实现方法 " />
本文介绍如何以最低计算开销将 `list
在高并发或大数据量场景下,flatMap 流式操作虽语义清晰,但会引入额外的装箱/拆箱、中间流对象创建及多次 ArrayList 动态扩容(每次扩容需数组复制),显著增加 CPU 开销;而朴素的 forEach + addAll 虽更直接,若未预设容量,仍会在内部反复调用 Arrays.copyOf(),造成可观的内存拷贝成本。
最优实践:预计算总容量 + 手动遍历添加
// 1. 预计算所有子列表大小之和(O(n) 时间,但无对象创建开销)
int expectedSize = parentList.stream()
.mapToInt(obj -> obj.getChildList().size())
.sum();
// 2. 初始化目标列表,指定精确初始容量
List result = new ArrayList<>(expectedSize);
// 3. 遍历并批量添加,避免扩容
for (Object obj : parentList) {
result.addAll(obj.getChildList());
} ✅ 优势分析:
数因子放大。⚠️ 注意事项:
对比小结:
| 方法 | 时间开销 | 内存开销 | 可读性 | 推荐场景 |
|--------|-----------|------------|-------------|------------------|
| stream().flatMap().collect() | 高(多层对象+扩容) | 高(临时流节点、collector 中间态) | 高 | 原型开发、数据量极小 |
| forEach + addAll()(无预容量) | 中高(频繁扩容复制) | 中(多次数组复制) | 中 | 快速验证,非瓶颈路径 |
| 预容量 + 显式循环 | 最低(纯遍历+单次分配) | 最低(无冗余对象) | 中高 | 生产环境高频调用核心路径 |
综上,当性能是首要约束时,显式容量预估 + 批量添加是目前 JVM 上最轻量、最可控的扁平化方案。