在前端开发中,我们通常需要将一个对象复制到另一个变量或对象中。ECMAScript 2017 为我们提供了两种对象拷贝方式:深拷贝和浅拷贝。本文将详细介绍这两种拷贝方式,并讨论它们的区别以及在什么情况下应该使用它们。
浅拷贝
浅拷贝是指将对象的第一层属性复制到新对象中,但不会复制嵌套的对象引用。这意味着,新对象和原对象共享同一嵌套对象,而对于嵌套对象的更改将影响所有引用它的对象。
以下是一个简单的例子来说明浅拷贝的概念:
-- -------------------- ---- ------- ----- -------------- - - -- -- -- - -- - - -- ----- ------------ - ----------------- ---------------- -- ---------- ---------------- - -- -------------------------- -- - -- -- -- - -- - - - ---------------------------- -- - -- -- -- - -- - - -
在上面的例子中,通过 Object.assign()
方法对 originalObject
进行浅拷贝,生成了一个拥有相同属性的新对象 copiedObject
。接着,我们更改了copiedObject
的嵌套对象 b
中的 c
属性值为 3 ,然后输出了两个变量的值。由于浅拷贝只是对第一层属性进行了复制,所以两个对象共享同一个嵌套对象,导致原对象中的属性也被更改。
因此,浅拷贝适用于对象比较简单时使用,例如基本数据类型属性或无需更改嵌套对象的情况下。注意当处理类似数组、Date 对象等引用类型时,浅拷贝可能会出现问题。
深拷贝
深拷贝不仅复制了对象的第一层属性,还复制了嵌套的对象引用,从而产生一个完全独立的对象。这意味着,对新对象或原始对象中的嵌套对象进行更改不会影响另一个对象。
以下是一个使用 JSON.parse()
和 JSON.stringify()
进行深拷贝的示例:
-- -------------------- ---- ------- ----- -------------- - - -- -- -- - -- - - -- ----- ------------ - ------------------------------------------- -- ---------- ---------------- - -- -------------------------- -- - -- -- -- - -- - - - ---------------------------- -- - -- -- -- - -- - - -
在上面的例子中,我们首先将原始对象 originalObject
转换为一个字符串,再通过 JSON.parse()
将其解析为新对象 copiedObject
。由于使用了深拷贝,因此更改 copiedObject
中嵌套对象 b
的 c
属性值不会影响原始对象中的属性。
需要注意的是,使用 JSON.parse()
和 JSON.stringify()
进行深拷贝时,会忽略非法格式的值,例如 undefined、function 等,在拷贝后对象中将不存在这些属性。同时也无法处理循环嵌套对象的情况,因为 JSON 不支持序列化循环引用的对象。
结论
综上所述,浅拷贝和深拷贝都有自己适用的场景
来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/67241dd82e7021665e12609a