Java中克隆ArrayList推荐用构造方法new ArrayList(original)实现浅拷贝;clone()需强转且语义模糊;深拷贝需手动遍历克隆元素或用序列化等方案;直接赋值和synchronizedList不是克隆。

Java 中克隆 ArrayList 有多种方式,关键看是否需要**浅拷贝**还是**深拷贝**。绝大多数场景下,只需浅拷贝(即复制集合结构和引用,不复制元素对象本身),推荐使用构造方法或 new ArrayList(original)。
用构造方法创建新 ArrayList(最常用、推荐)
这是最简洁、安全且语义清晰的方式,底层调用 addAll(),生成一个内容相同但独立的新集合:
ArrayList<String> original = new ArrayList<>(Arrays.asList("a", "b", "c"));
ArrayList<String> copy = new ArrayList<>(original);
✅ 优点:代码简短、线程安全无关(非同步操作)、兼容所有 JDK 版本。
⚠️ 注意:这是浅拷贝——如果元素是可变对象(如自定义类实例),修改原集合中某个元素的状态,副本中对应元素也会“看到”变化(因为引用相同)。
用 clone() 方法(需注意类型转换和局限性)
ArrayList.clone() 返回的是 Object,必须强制转型,且仅支持浅拷贝:
立即学习“Java免费学习笔记(深入)”;
ArrayList<String> original = new ArrayList<>(Arrays.asList("x", "y"));
ArrayList<String> copy = (ArrayList<String>) original.clone();
❌ 缺点:返回类型不安全(需强转)、clone() 在 Java 中语义模糊,部分集合实现可能未正确重写;
✅ 优点:性能略快(直接数组复制),但差异微乎其微,一般无需为此选它。
需要深拷贝时怎么办?
当 ArrayList 中的元素是**可变对象**(比如 Person、HashMap 等),且你希望副本与原集合完全隔离(改副本不影响原集合,反之亦然),就必须手动深拷贝:
- 若元素类实现了
Cloneable并重写了clone(),可遍历复制:
ArrayList<Person> original = ...;
ArrayList<Person> deepCopy = new ArrayList<>();
for (Person p : original) {
deepCopy.add((Person) p.clone()); // 假设 Person 正确实现了深 clone
}
- 更稳妥的方式是用构造函数或工厂方法创建新对象(如
new Person(p.getName(), p.getAge())); - 对于嵌套复杂结构,可考虑序列化(如 JSON 字符串转出再解析)或使用 Lombok 的
@Builder+toBuilder等工具辅助。
不建议的方式:直接赋值或使用 Collections.synchronizedList
错误示例:
ArrayList<String> copy = original; // ❌ 只是引用复制,不是克隆!
这会让两个变量指向同一个对象,任何修改都会相互影响。Collections.synchronizedList() 是加锁包装,不产生新集合,也不用于克隆。


















