system.arraycopy 是 java 中唯一能绕过 java 层循环与边界检查、直连 jvm 底层内存搬运指令的原语,仅当用于基本类型数组(≥256)、对象数组引用拷贝、目标数组已预分配且 length 为编译期常量等条件下,才真正实现高性能;参数任一越界或类型不兼容即抛异常,不静默失败。

System.arraycopy 是 Java 中真正能“提速”的数组拷贝方式,但它的快,是有条件的——不是写上就快,而是用对才快。它跳过 Java 层循环和逐元素检查,直连 JVM 底层内存搬运指令,但参数错一个、场景选不对,反而比 for 循环还慢。
什么时候用 arraycopy 才真快
它优势明显,但只在特定条件下兑现:
- 基本类型数组(int[]、byte[] 等)长度 ≥ 256 时,JVM 常启用 SIMD 指令批量搬运,速度跃升
- 对象数组(String[]、自定义类[])拷贝也快,因为只复制引用,不触发 GC 写屏障,适合高频状态快照
- 目标数组必须已预先分配好,且长度足够:arraycopy 不扩容、不建新数组,只搬数据
- length 尽量用编译期常量(如 1024),利于 JIT 内联与向量化;若来自变量,可加小数据分支(≤16 用 for)
安全拷贝的关键参数控制
五个参数顺序固定、含义明确,任一越界或类型不匹配,运行时立刻抛异常,不静默失败:
- src 和 dest 都不能为 null,否则 NullPointerException
- srcPos ≥ 0 且 srcPos + length ≤ src.length,否则 ArrayIndexOutOfBoundsException
- destPos ≥ 0 且 destPos + length ≤ dest.length,否则同上
- 源目标类型必须兼容:int[] → long[] 不行;String[] → Object[] 可以;Object[] → String[] 报 ArrayStoreException
- length = 0 合法,可用于边界预检,零开销
原地移动:不用判断方向,JVM 自动处理
同一数组内移位(如删除元素后前移、RingBuffer 左右滑动),无需手写正向/倒序逻辑:
- 左移(destPos
- 右移(destPos > srcPos):System.arraycopy(arr, 2, arr, 5, 5) → JVM 自动倒序搬运,防止中间数据丢失
- 只要满足 srcPos + length ≤ arr.length 且 destPos + length ≤ arr.length,重叠区间就安全
比 Arrays.copyOf 和 clone() 更省的场景
当目标数组已存在、长度已知、只需搬数据时,arraycopy 是唯一零分配选择:
- Arrays.copyOf(src, len) 会 new 新数组,带来堆分配和 GC 压力
- clone() 只支持整数组复制,无法指定起始位置或长度,也不能复用已有 dst 数组
- 正确做法:提前分配好 dst(如 int[] dst = new int[1000]),再 System.arraycopy(src, off, dst, 0, len)
- 典型适用:滑动窗口缓存更新、多轮模拟状态迁移、ArrayList 扩容迁移有效元素
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











