浅拷贝通过Cloneable接口由JVM原生支持,仅复制基本类型值和引用地址;深拷贝依赖序列化实现“重建式”复制,彻底独立但性能开销大、要求类可序列化且无法还原运行时状态。

浅拷贝用 Cloneable 接口是 JVM 层面的轻量复制,只管字段一层;深拷贝走序列化是绕过引用关系的“重建式”复制,代价高但彻底独立。
Cloneable 实现的是默认浅拷贝
实现 Cloneable 并重写 clone(),本质是调用 super.clone() —— 这个方法由 JVM 原生支持,行为固定:
- 基本类型字段(
int、boolean等)值被完整复制 - 引用类型字段(如
Address、ArrayList)只复制内存地址,新旧对象共用同一实例 - 不检查子类新增的引用字段,若父类未处理好,容易漏拷贝
序列化实现的是强制深拷贝
把对象写成字节流再读回来,等于“销毁再重建”,天然切断所有引用链:
- 要求整个对象图中每个类都实现
Serializable - 跳过
transient字段和不可序列化成员(如Thread、Socket) - 无法还原运行时状态(比如打开的数据库连接、线程局部变量)
- 性能开销明显:涉及 I/O、反射、类加载,对象越深越慢
名字带 clone 不代表就是深拷贝
很多工具方法容易误导:
-
SerializationUtils.clone()底层仍是序列化,满足可序列化才安全 -
BeanUtils.cloneBean()是反射+浅拷贝,对嵌套对象完全不处理 -
ObjectMapper.readValue(..., type)(Jackson)靠 JSON 中转,需类结构稳定、无循环引用,且Date等类型要配好序列化器
真正可控但少用的手动深拷贝
递归遍历字段 + 类型判断 + 分支新建,理论上最灵活:
- 能跳过特定字段、定制集合元素复制逻辑、处理循环引用
- 但极易出错:漏字段、错判
final或泛型擦除类型、栈溢出 - 实际项目几乎不用,除非有极特殊的数据隔离需求















