浅拷贝只复制第一层属性,嵌套对象仍共享内存;深拷贝递归重建所有层级,新旧对象彻底隔离。选型取决于数据是否嵌套、含特殊类型或循环引用,以及性能要求:扁平结构用展开运算符或Object.assign();需完全隔离时优先structuredClone(),兼容旧环境用lodash.cloneDeep(),禁用JSON方案处理复杂数据。

浅拷贝只复制第一层属性,嵌套对象仍共享内存;深拷贝则递归重建所有层级,新旧对象彻底隔离。选哪种,关键看数据结构是否嵌套、是否含特殊类型(如 Date、Map)、有没有循环引用,以及性能是否敏感。
浅拷贝的适用场景与常用写法
当确定数据是扁平结构(无嵌套对象或数组),或仅需临时解构、只读使用时,浅拷贝更轻量高效。
-
展开运算符(...):适合对象和数组,语法简洁,如
const newObj = { ...oldObj }或const newArr = [...oldArr] -
Object.assign():可合并多个源对象,
Object.assign({}, obj)常用于对象浅拷贝 -
数组方法:如
slice()、concat()、Array.from(),都返回新数组,但内部元素仍是原引用
深拷贝的可靠实现路径
需要完全隔离数据时,不能依赖“快捷方式”,得按场景选方案:
- structuredClone():现代浏览器(Chrome 98+、Safari 16.4+、Firefox 94+)原生支持,能正确处理 Map、Set、Date、RegExp、BigInt、TypedArray 和循环引用,是目前最推荐的通用方案
- Lodash 的 _.cloneDeep():兼容性好,覆盖全面,适合还需支持老旧环境的项目
- 手写递归 + WeakMap:适合学习原理或定制需求(如过滤某些字段、保留原型链),核心是用 WeakMap 缓存已遍历对象,避免循环引用死循环,并对 Date、RegExp、Map 等类型分别构造新实例
- JSON.parse(JSON.stringify()):仅限简单数据,会丢掉 function、undefined、Symbol、Date 对象变字符串、Map/Set 消失,且不支持循环引用——生产环境慎用
怎么快速判断该用哪一种?
先问三个问题:
- 数据里有没有嵌套对象或数组?有 → 浅拷贝不够用
- 有没有 Date、正则、Map、Set 或自定义类实例?有 → 避开 JSON 方案
- 是否可能形成循环引用(比如父子关系对象)?有 → 必须用 structuredClone 或带缓存的手写逻辑
多数业务场景下,优先尝试 structuredClone();需要兼容 IE 或老版移动端时,引入 Lodash;纯学习或特殊定制再考虑手写。


















