该方法可以实现对对象、数据、日期、正则等的深拷贝
直接上代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>深拷贝</title>
</head>
<body>
<script>
// WeakMap 对象是一组键/值对的集合,其中的键是弱引用的。其键必须是对象,而值可以是任意的。
// https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/WeakMap
function deepCopy (obj, cache = new WeakMap()) {
if (!obj instanceof Object) {
return obj;
}
// 防止循环引用
if (cache.get(obj)) {
return cache.get(obj)
}
// 支持函数
if (obj instanceof Function) {
return function () {
obj.apply(this, arguments);
}
}
// 支持日期
if (obj instanceof Date) {
return new Date(obj)
}
// 支持正则对象
if (obj instanceof RegExp) {
return new RegExp(obj.source, obj.flags)
}
// 还可以增加其他对象,比如:map, set 等,根据情况判断增加极客
// 数组是 key 为数字的特殊对象
const res = Array.isArray(obj) ? [] : {}
// 缓存 copy 的对象,用于处理循环引用的情况
cache.set(obj, res)
Object.keys(obj).forEach(key => {
if (obj[key] instanceof Object) {
res[key] = deepCopy(obj[key], cache)
} else {
res[key] = obj[key]
}
})
return res
}
// 测试身边拷贝
const source = {
name: 'Jack',
meta: {
age: 12,
birth: new Date('1997-10-10'),
ary: [1, 2, { a: 1 }],
say() {
console.log('Hello');
}
}
}
source.source = source;
console.log('原始数据', source)
const deepObject = deepCopy (source);
console.log('深拷贝数据', deepObject)
console.log('判断其中数据是否相同-1', deepObject.meta.ary[2] === source.meta.ary[2])
console.log('判断其中数据是否相同-2', deepObject.source === source.source)
</script>
</body>
</html>
有什么不同的意见,请及时评论,共同学习……