Java二维数组深拷贝需重建内层数组,因clone()和Arrays.copyOf()仅复制外层引用导致共享子数组;安全方式为外层数组新建+每行单独拷贝,如循环调用Arrays.copyOf或每行clone()。

Java 二维数组的拷贝不是简单调用 clone() 或 Arrays.copyOf() 就能安全完成的。真正的问题在于:**二维数组本质是“一维引用数组”,而多数拷贝方式只复制了外层引用,没重建内层数组对象**——这导致看似独立的两个数组,修改时却相互影响。
浅拷贝的典型表现
执行 int[][] b = a.clone(); 后:
-
a != b(顶层数组对象不同) -
a[0] == b[0](第一行指向同一块内存) -
a[1] == b[1](第二行也共享引用) - 修改
b[0][0],a[0][0]立刻同步变化
为什么 clone() 和 arraycopy() 都是“假深拷贝”
它们只作用于外层数组:
Java Maven 项目审查工作流的通用输入处理。当 Java Maven 项目以 ZIP压缩包或 GitLab 仓库 URL 形式提供且需要...时使用。
-
clone()对int[][]是 bitwise copy,复制的是a[0]、a[1]这些地址值,而非其指向的int[]实例 -
System.arraycopy(a, 0, b, 0, a.length)同样只搬运外层数组的引用元素,子数组仍共用 - 对基本类型(如
int)的内层数组,这种共享不易察觉;但一旦涉及可变对象(如Person[]),风险立刻暴露
验证是否真隔离的关键测试
不能只看 b != a,必须检查子数组层级:
立即学习“Java免费学习笔记(深入)”;
- 修改
b[0][0]后,确认a[0][0]值未变 - 断言
a[0] == b[0]应为false - 断言
a[0].length == b[0].length且内容一致,但对象身份不同
真正安全的拷贝方式
核心:外层新建数组 + 每行单独创建并填充
-
手动循环 + Arrays.copyOf:
dst[i] = Arrays.copyOf(src[i], src[i].length); -
arraycopy 配合新建行:
dst[i] = new int[src[i].length]; System.arraycopy(src[i], 0, dst[i], 0, src[i].length); -
每行调用 clone():
dst[i] = src[i].clone();(简洁且对基本类型安全) - 若含自定义对象,需确保其自身支持深拷贝(如实现
Cloneable并重写clone())

















