一次javascript深拷贝引发的深入思考

简介: js深拷贝深入思考

A同学和B同学因为一次js深拷贝发生的一次争执。

A同学:深拷贝是另一个对象占用另一块内存就行了,随手写出了如下代码:


leta= {
name: "lcy",
age: 18};
letb=Object.assign({}, a);
console.log(JSON.stringify(b, null, 2));
letc= {};
for (letkeyina) {
c[key] =a[key];
}
console.log(JSON.stringify(c, null, 2));
b.name="123";
c.name="456";
console.log(JSON.stringify(a, null, 2));
console.log(JSON.stringify(b, null, 2));
console.log(JSON.stringify(c, null, 2));


image.gif

image.gif


B同学:突然一看这两种方法好像确实都是深拷贝,bc对象修改属性后对a对象没什么影响,但是也会面临其他问题,如下


leta= {
name: "lcy",
age: 18,
user: {
u: "uu_c"    }
};
letb=Object.assign({}, a);
letc= {};
for (letkeyina) {
c[key] =a[key];
}
b.user.u="123";
console.log(JSON.stringify(a));
console.log(JSON.stringify(b));
console.log(JSON.stringify(c));
c.user.u="456";
console.log(JSON.stringify(a));
console.log(JSON.stringify(b));
console.log(JSON.stringify(c));

image.gif


image.gif


我们会发现,这种方式如果属性值是对象的话,那么这个对象是浅拷贝的,并么有完全深拷贝。


于是A同学灵机一动,迅速展示思维能力,随手就是一个代码~


leta= {
name: "lcy",
age: 18,
user: {
u: "uu_c"    }
};
functiondeepClone(obj) {
letres= {};
for (letkeyinobj) {
res[key] =typeofobj[key] =="object"?deepClone(obj[key]) : obj[key];
    }
returnres;
}
letb=deepClone(a);
console.log(JSON.stringify(a));
console.log(JSON.stringify(b));
b.user.u="123";
console.log(JSON.stringify(a));
console.log(JSON.stringify(b));

image.gif


image.gif


A同学拍拍胸脯,搞定,然后B同学问,万一你这个拷贝的源对象属性是它原型上的呢?我们可能并不需要原型上的属性


A同学:那就在for循环的时候加一个判断,if(obj.hasOwnProperty(key))就行了,其他代码不用动,这个可难不倒我。


B同学:你要不加个数组到a对象试试,如下


leta= {
name: "lcy",
age: 18,
user: {
u: "uu_c"    },
arr: [1, 3, 5]
};
functiondeepClone(obj) {
letres= {};
for (letkeyinobj) {
if (obj.hasOwnProperty(key)) {
res[key] =typeofobj[key] =="object"?deepClone(obj[key]) : obj[key];
        }
    }
returnres;
}
letb=deepClone(a);
console.log(JSON.stringify(a));
console.log(JSON.stringify(b));

image.gif


image.gif



这一下把A同学干懵了,居然数组还有这一情况,typeof 数组类型也是object,看来不能简单的判断object类型,于是A同学深思熟虑之后终于写出了如下代码


leta= {
name: "lcy",
age: 18,
user: {
u: "uu_c"    },
arr: [1, 3, 5]
};
functiondeepClone(obj) {
letres=objinstanceofArray? [] : {};
for (letkeyinobj) {
if (obj.hasOwnProperty(key)) {
res[key] =typeofobj[key] =="object"?deepClone(obj[key]) : obj[key];
        }
    }
returnres;
}
letb=deepClone(a);
console.log(JSON.stringify(a));
console.log(JSON.stringify(b));

image.gif


image.gif



最后B同学看了一下,反手一巴掌对着A的后脑勺狠狠地给他点了个赞,说干得漂亮!



关注、留言,我们一起学习。


===============Talk is cheap, show me the code================

目录
相关文章
|
8月前
|
JSON JavaScript 数据格式
深拷贝和浅拷贝(js的问题)
深拷贝和浅拷贝(js的问题)
37 0
|
3月前
|
JavaScript 前端开发
JavaScript中的深拷贝与浅拷贝
JavaScript中的深拷贝与浅拷贝
55 4
|
4月前
|
JSON JavaScript 数据格式
手写JS实现深拷贝函数
本文介绍了如何实现一个深拷贝函数`deepClone`,该函数可以处理对象和数组的深拷贝,确保拷贝后的对象与原始对象在内存中互不干扰。通过递归处理对象的键值对和数组的元素,实现了深度复制,同时保留了函数类型的值和基础类型的值。
28 3
|
5月前
|
JavaScript 前端开发
JavaScript中的深拷贝与浅拷贝
JavaScript中的深拷贝与浅拷贝
48 2
|
5月前
|
JavaScript 前端开发
JavaScript中的深拷贝和浅拷贝的实现讲解
在JavaScript中,浅拷贝与深拷贝用于复制对象。浅拷贝仅复制基本类型属性,对于引用类型仅复制引用,导致双方共享同一数据,一方修改会影响另一方。深拷贝则完全复制所有层级的数据,包括引用类型,确保双方独立。浅拷贝可通过简单属性赋值实现,而深拷贝需递归复制各层属性以避免共享数据。
77 1
|
7月前
|
JSON JavaScript 前端开发
【JavaScript】JavaScript中的深拷贝与浅拷贝详解:基础概念与区别
JavaScript 中,理解数据拷贝的深浅至关重要。浅拷贝(如扩展运算符`...`、`Object.assign()`)仅复制对象第一层,共享内部引用,导致修改时产生意外联动。深拷贝(如自定义递归函数、`_.cloneDeep`或`JSON.parse(JSON.stringify())`)创建独立副本,确保数据隔离。选择哪种取决于性能、数据独立性和资源需求。深拷贝虽慢,但确保安全;浅拷贝快,但需小心引用共享。在面试中,理解这些概念及其应用场景是关键。
142 4
【JavaScript】JavaScript中的深拷贝与浅拷贝详解:基础概念与区别
|
5月前
|
JavaScript 前端开发
js中浅拷贝和深拷贝的区别
js中浅拷贝和深拷贝的区别
33 0
|
5月前
|
JavaScript 前端开发
js中浅拷贝,深拷贝的实现
js中浅拷贝,深拷贝的实现
39 0
|
6月前
|
JavaScript
js【详解】深拷贝 (含 JSON.parse(JSON.stringify(obj)) 的缺陷,5种手写深拷贝)
js【详解】深拷贝 (含 JSON.parse(JSON.stringify(obj)) 的缺陷,5种手写深拷贝)
190 0
|
6月前
|
存储 JavaScript 前端开发
javascript的栈内存 VS 堆内存(浅拷贝 VS 深拷贝)
javascript的栈内存 VS 堆内存(浅拷贝 VS 深拷贝)
34 0