arrays.copyof 是“长度驱动”的数组拷贝工具,用于扩容、截断或快速备份,不适用于取中间段或深拷贝;需注意 null 输入抛异常、小数组建议手动循环、引用类型为浅拷贝。

Arrays.copyOf 不是“万能扩容键”,而是有明确语义的工具:它创建新数组、复制指定长度内容、自动补默认值。用对了,能简化逻辑、减少出错;用错了,反而引入冗余对象和 GC 压力。
适合场景:扩容、截断、快速备份
它本质是“长度驱动”的拷贝——你告诉它要多长,它就按需取前 N 个或补零/null。不是用来取中间一段,也不是用来往已有缓冲区里写。
- 扩容:原数组不够用,比如日志缓冲区动态增长,
Arrays.copyOf(logs, logs.length + 1024)直接得到更大空间,空位填 0 或 null - 截断:只保留前 N 条,如分页取前 20 条记录,
Arrays.copyOf(data, 20)比手算长度再 new 更安全 - 快速备份:需要一份独立副本且长度不变,
Arrays.copyOf(original, original.length)比 clone() 少一次类型转换,语义也更直白
避坑要点:别把它当 copyOfRange 用
很多人误以为 copyOf(arr, 5) 能取索引 2~6,其实它永远从 0 开始拷。想截中间?必须用 copyOfRange(arr, 2, 7)(左闭右开)。
- newLength 小于原数组长度 → 截前段,不抛异常
- newLength 大于原数组长度 → 后面补默认值,不会越界
- newLength 为 0 → 返回空数组,不是 null
- 传入 null → 直接抛 NullPointerException,不帮你兜底
性能边界:小数据量不如直接赋值
拷贝几十个元素时,JVM 调用 native 方法的开销可能比纯 Java 循环还高。尤其在高频调用路径(如解析每条网络包),建议加阈值判断:
- 长度 ≤ 16:直接 for 循环赋值,代码清晰且 JIT 可能优化掉边界检查
- 长度 > 16:交给 Arrays.copyOf,它内部调用高度优化的 System.arraycopy
- 循环内反复调用 copyOf → 改用复用目标数组 + System.arraycopy,避免频繁 new
对象数组要注意:仍是浅拷贝
对 String[]、User[] 这类引用类型数组,copyOf 只复制引用,不复制对象本身。多数业务没问题,但若后续会修改元素内容并希望隔离,就得另做处理。
- String 是不可变的,浅拷贝即等效深拷贝
- User[] 浅拷贝后,
copy[0].setName("xxx")会影响原数组对应对象 - 真需深拷贝嵌套结构,用 SerializationUtils.clone() 或手动遍历 clone,别指望 copyOf 自动递归
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











