Javascript 深拷贝对象

阅读时长 3 分钟读完

在 JavaScript 中,当我们创建一个对象并将其赋值给另一个变量时,通常情况下,它们会共享同一个内存地址。这意味着如果你更改其中一个变量的属性或值,另一个变量也会受到影响。为了避免这种意外行为,我们需要进行深层次的对象拷贝。

浅拷贝和深拷贝

在开始讨论深拷贝之前,我们需要先了解浅拷贝和深拷贝的区别。

浅拷贝是指创建一个新对象,这个新对象有着原始对象属性值的一份精确的拷贝。但如果属性是引用类型,那么新对象的这个属性仍然指向原始对象中相应的属性。这意味着如果更改了新对象中的这个属性,原始对象也会受到影响。

深拷贝是指创建一个新对象,这个新对象有着原始对象属性值的一份精确的拷贝。但是,如果属性是引用类型,那么新对象的这个属性也会被递归地复制,直到所有引用类型的属性都被复制为止。这意味着即使更改了新对象中的这个属性,原始对象也不会受到影响。

实现深拷贝

现在我们来看一下如何实现深拷贝。这里介绍两种方法:递归和 JSON 序列化。

递归

递归是实现深拷贝的传统方法,也是最常用的方法之一。它可以处理任何类型的对象,包括嵌套的对象和数组。下面是一个示例:

-- -------------------- ---- -------
-------- ------------- -
  -- ------- --- --- -------- -- --- --- ----- -
    ------ ----
  -
  ----- ------ - ------------------ - -- - ---
  --- ---- --- -- ---- -
    -- ------------------------------------------ ----- -
      ----------- - -------------------
    -
  -
  ------ -------
-

该函数接受一个对象作为参数,并返回其深拷贝的副本。如果对象不是对象或者是 null,则直接返回该对象。否则,创建一个新对象,并通过递归调用 deepCopy 函数将每个属性的值复制到新对象中。

JSON 序列化

使用 JSON 序列化进行深拷贝是一个简单而快捷的方法,但是它有一些限制。首先,它只能序列化可转换为 JSON 的数据类型,例如字符串、数字、布尔值、数组、对象和 null。其次,它不能序列化包含循环引用的对象,因为它会导致无限递归。最后,它不能保留对象的原型链和方法,因为它只能序列化对象的属性。

下面是一个使用 JSON 序列化进行深拷贝的示例:

该函数接受一个对象作为参数,并返回其深拷贝的副本。JSON.stringify 将对象转换为字符串,然后 JSON.parse 将字符串转换回对象。这将创建一个新对象,其中包含原始对象中所有的属性和值。由于 JSON.stringify 和 JSON.parse 都会断开对象的原型链,因此新对象不会继承原始对象的方法或原型。

总结

在 JavaScript 中,深层次地拷贝对象是一项非常重要的技能。通过深拷贝,我们可以避免修改对象时出现意外行为,从而增强代码的可读性和稳

来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/29267

纠错
反馈