JS对象赋值会影响原对象解决办法 您所在的位置:网站首页 js给一个对象赋值 JS对象赋值会影响原对象解决办法

JS对象赋值会影响原对象解决办法

2023-12-31 02:00| 来源: 网络整理| 查看: 265

JS常见坑:对象赋值会影响原对象

现象:直接用=的方式把一个对象赋值给另一个对象,会导致修改新对象时,原对象也发生变化

var obj1 = {'name': '1111'}; var obj2 = obj1; obj2.name = '2222'; console.log(obj1.name); //'2222'

原因:JavaScript 中对象的赋值是默认引用赋值的(两个对象指向相同的内存地址)

一、Object.assign()拷贝对象 代码演示 // 使用 Object.assign() 方法复制对象 let obj1 = { a: 0 , b: { c: 0}}; let obj2 = Object.assign({}, obj1); console.log(JSON.stringify(obj2)); // { a: 0, b: { c: 0}} obj2.a = 2; console.log(JSON.stringify(obj1)); // { a: 1, b: { c: 0}} console.log(JSON.stringify(obj2)); // { a: 2, b: { c: 0}} obj2.b.c = 3; console.log(JSON.stringify(obj1)); // { a: 1, b: { c: 3}} console.log(JSON.stringify(obj2)); // { a: 2, b: { c: 3}} 不足之处 可以看到当修改obj2.b.c的值时,原对象obj1.b.c也跟着发生了变化,Object.assign()只是让对象里第一层的数据没有了关联性,但是对象内的对象则跟被复制的对象有着关联性的。 Object.assign(obj) --浅拷贝 Object.assign({},obj) --只有第一层深拷贝 (ES6中扩展运算符...也是如此) 二、JSON.parse(JSON.stringify(obj)) 代码演示 var function cloneObjectFn (obj){ return JSON.parse(JSON.stringify(obj)) } var obj1={a:2,b{c:0}} var obj2=cloneObjectFn(obj1) console.log(obj2) // {a:2,b{c:0}} 不足之处

使用场景限制:obj属性不能是function、RegExp等,JSON序列化时会造成属性丢失: image

三、原生JS实现深拷贝 // 定义一个深拷贝函数 接收目标target参数 function deepClone(target) { // 定义一个变量 let result; // 如果当前需要深拷贝的是一个对象的话 if (typeof target === 'object') { // 如果是一个数组的话 if (Array.isArray(target)) { result = []; // 将result赋值为一个数组,并且执行遍历 for (let i in target) { // 递归克隆数组中的每一项 result.push(deepClone(target[i])) } // 判断如果当前的值是null的话;直接赋值为null } else if (target === null) { result = null; // 判断如果当前的值是一个RegExp对象的话,直接赋值 } else if (target.constructor === RegExp) { result = target; } else { // 否则是普通对象,直接for in循环,递归赋值对象的所有值 result = {}; for (let i in target) { result[i] = deepClone(target[i]); } } } else { // 如果不是对象的话,就是基本数据类型,那么直接赋值 result = target; } // 返回最终结果 return result; }

PS. JS中function也是引用类型,但是函数名仅仅是指向该函数的指针,换句话说,一个函数可能会有多个名字

function sum(num1, num2){ return num1 + num2; } console.log(sum(10, 10));// 20 var anotherSum = sum; // 此时有两个变量sum和anotherSum同时指向该函数(该函数此时有俩名字) console.log(anotherSum(10, 10));// 20 sum = null; // sum置为空后,此时只有anotherSum指向该函数(该函数只有一个名字anotherSum) console.log(anotherSum(10, 10));// 20

如上:代码中首先定义了一个名为sum的函数,用于求两个数的和。然后,又声明了变量anotherSum,赋值为sum,此时anotherSum和sum就指向了同一个函数,因此anotherSum()也正常返回了结果。即使切断sum与函数对象的引用关系,也不会影响anotherSum



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有