json.parse(json.stringify(obj))仅适用于纯json类型数据的深拷贝,不支持函数、undefined、date等;现代环境推荐structuredclone(),兼容性需求可选lodash.clonedeep或weakmap实现的自定义方案。

用 JSON.parse(JSON.stringify(obj)) 可以实现简单对象的深拷贝,但它只适用于“可 JSON 序列化”的数据,不适用于函数、undefined、Symbol、Date、RegExp、Map、Set、BigInt 或循环引用等类型。
适用场景:纯数据对象和数组
当对象只包含字符串、数字、布尔值、null、普通对象、普通数组(即 JSON 支持的类型)时,这种方式简洁有效:
- 避免了引入第三方库或手写递归逻辑
- 代码一行搞定:
const deepCopy = JSON.parse(JSON.stringify(original)); - 对嵌套层级较深但结构干净的数据效果稳定
常见失效情况(务必注意)
以下内容在 JSON 序列化过程中会被忽略、转换或报错:
-
函数和 undefined:被直接丢弃(如
{ a: 1, b: () => {} }拷贝后变成{ a: 1 }) -
Date 对象:转成字符串(
new Date()→"2024-05-20T10:30:00.000Z"),不再是 Date 实例 -
正则表达式:序列化为
{},丢失所有信息 -
NaN、Infinity、-Infinity:转为
null -
循环引用:直接抛出
TypeError: Converting circular structure to JSON - Map / Set / WeakMap / WeakSet / BigInt / Symbol:无法序列化,会报错或丢失
简单验证是否适用的小技巧
可在拷贝前快速检查对象是否“安全”:
function isJSONSafe(obj) {
try {
JSON.stringify(obj);
return true;
} catch {
return false;
}
}
如果 isJSONSafe(obj) 返回 false,就不要用这个方法,改用 structuredClone(现代浏览器)、lodash.cloneDeep 或自定义深拷贝函数。
替代建议(更健壮的选择)
-
现代环境优先用
structuredClone():支持 Map、Set、Date、RegExp、ArrayBuffer 等,且能处理循环引用(Chrome 98+、Firefox 94+、Safari 15.4+) -
需要兼容老浏览器? 用 Lodash 的
_.cloneDeep(),覆盖类型全面,经过大量测试 -
自己实现? 避免简单递归(易栈溢出/无循环处理),推荐基于
WeakMap记录已拷贝引用的递归函数
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











