lodash 插件 cloneDeep
浅拷贝:
数组:slice()/concat()/Array.from()/扩展运算符
对象:Object.assign()/扩展运算符
深拷贝:
- 通过 JSON.parse(JSON.stringify(obj))
这种方法只能复制 JSON 格式支持的属性名和值,不支持的属性名和值会直接忽略:会忽略 undefined、symbol,不能序列化函数,不能解决循环引用的对象 参考MDN
JSON.parse(JSON.stringify({ [Symbol('a')]: 'abc', b: function() {}, c: undefined, d: Infinity, e: NaN, }))
|
function deepCopy(source) { if (Array.isArray(source)) { const target = [] for (const [index, value] of source.entries()) { target[index] = deepCopy(value) } return target
} else if (typeof source === 'object' && source !== null) { const target = {} for (const [key, value] of Object.entries(source)) { target[key] = deepCopy(value) } return target
} else { return source } }
|
Object.fromEntries()
方法把键值对列表转换为一个对象,是 Object.entries
的反转
循环引用(环)
解决思路: 通过一个WeakMap来存储拷贝过的对象
let hash = new WeakMap() if (hash.has(source)) { return hash.get(source) }
hash.set(source, target)
|
特殊对象的拷贝
target = new Function(`return ${source.toString()}`)()
target = new Date(source.getTime())
target = new RegExp(source)
|