Javascript对象复制引用机制及$.extend复制特点

Stella981
• 阅读 632

首先复习一下javascript中的变量类型

基本类型

  • number
  • string
  • boolean
  • undefined
  • null

引用类型

  • function
  • array
  • date
  • 正则
  • 错误

基本类型变量的复制,内容修改后,不会对另一变量产生影响

var a = 1;

var b =a;

a = 2;

console.log(a);//2

console.log(b);//1

引用类型变量若将A对象内容赋值给B对象,则B对象只是A对象的引用,此时若修改了B的内容,A的内容也会随之变化

var a = {a:1,b:2};

var b = a;

b.b = 3;

console.log(a);//{a:1,b:3}

console.log(b);//{a:1,b:3}

以此得出的结论,在Javascript下,将一个对象类型变量赋值仅得到对象的引用。

但在某些情况下,出于对功能上的要求,必须要求变量在获得另一个对象的复制后,各自修改内容,不会互相影响;使用Javascript原生可参照以下方式:

var arr = {"a":"1","b":"2"};

var arr1 = arr;

arr = {};

arr["a"] = 2;

console.log(arr);//{"a":2}

console.log(arr1);//{"a":"1","b":"2"}

原理是A变量是B对象变量的引用时,将A置空,再为A设置内容,就不会再是B的引用

还可以利用JSON.stringify方法和jQuery的$.parseJSON方法进行处理(略麻烦)

var data = {a:1,b:2,c:3,d:[0,1,2,3]};

var str = JSON.stringify(data);

var data1 = $.parseJSON(str);

data1["e"] = 5;

data1["d"][0] = 22;

console.log(data);//{a: 1, b: 2, c: 3, d: [0,1,2,3]}

console.log(data1);//{a: 1, b: 2, c: 3, d: [22,1,2,3], e: 5}

这种转换的过程实际就是重新生成对象了

使用jQuery的$.extend()方法来扩展、复制对象

var a = {a:1,b:2};

var b = $.extend({},a);

b.b = 3;

console.log(a);//{a:1,b:2}

console.log(b);//{a:1,b:3}

以上的方式,若A变量的属性里还有子对象,比如:{a:1,b:2,c:{aa:11,bb:22}},在进行复制时,子对象的内容依然是引用的方式,会互相影响

var a = {a:1,b:2,c:{aa:11,bb:22}};

var b = $.extend({},a);

b.b = 3;

b.c.aa = 33;

console.log(a);//{a:1,b:2,c:{aa:33,bb:22}}

console.log(b);//{a:1,b:3,c:{aa:33,bb:22}}

使用$.extend()方法的深度复制方式,即可杜绝以上问题,使用深度复制,即使母对象中子对象有再多层级,依然会进行完整复制,并不会进行对象引用

var a = {a:1,b:2,c:{aa:11,bb:22}};

var b = $.extend(true,{},a);

b.b = 3;

b.c.aa = 33;

console.log(a);//{a:1,b:2,c:{aa:11,bb:22}}

console.log(b);//{a:1,b:3,c:{aa:33,bb:22}}
点赞
收藏
评论区
推荐文章
blmius blmius
3年前
MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1
文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s
Wesley13 Wesley13
3年前
java 复制Map对象(深拷贝与浅拷贝)
java复制Map对象(深拷贝与浅拷贝)CreationTime2018年6月4日10点00分Author:Marydon1.深拷贝与浅拷贝  浅拷贝:只复制对象的引用,两个引用仍然指向同一个对象
待兔 待兔
5个月前
手写Java HashMap源码
HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程22
Wesley13 Wesley13
3年前
java常用类(2)
三、时间处理相关类Date类:计算机世界把1970年1月1号定为基准时间,每个度量单位是毫秒(1秒的千分之一),用long类型的变量表示时间。Date分配Date对象并初始化对象,以表示自从标准基准时间(称为“历元”(epoch),即1970年1月1日08:00:00GMT)以来的指定毫秒数。示例:packagecn.tanjian
待兔 待兔
4年前
[Dart]Dart语言之旅<二>:变量
变量以下是创建变量并为其分配值的示例:varname'Bob';变量是引用。名为name的变量包含对值为“Bob”的String类型的对象的引用。默认值未初始化的变量的初始值为null。即使是数字类型的变量,初始值也为null,因为数字也是对象。intlineCount;assert(lineCountnull)
Wesley13 Wesley13
3年前
Java对象的浅拷贝和深拷贝&&String类型的赋值
Java中的数据类型分为基本数据类型和引用数据类型。对于这两种数据类型,在进行赋值操作、方法传参或返回值时,会有值传递和引用(地址)传递的差别。浅拷贝(ShallowCopy):①对于数据类型是基本数据类型的成员变量,浅拷贝会直接进行值传递,也就是将该属性值复制一份给新的对象。因为是两份不同的数据,所以对其中一个对象的该成员变量值进行修改,
Stella981 Stella981
3年前
JavaScript学习小结
JavaScirpt变量可用来保存两种类型值:基本类型值,引用类型值基本类型值:Undefined,Null,Boolean,Number,String基本类型及引用类型值特点:1.基本类型值在内存中占据固定大小的空间,被保存在栈内存中;2.从一个变量向另一个变量复制基本类型值,会创建这个值的一个副本;
Stella981 Stella981
3年前
JVM调优总结一
数据类型   Java虚拟机中,数据类型可以分为两类:基本类型和引用类型。基本类型的变量保存原始值,即:他代表的值就是数值本身;而引用类型的变量保存引用值。“引用值”代表了某个对象的引用,而不是对象本身,对象本身存放在这个引用值所表示的地址的位置。基本类型包括:byte,short,int,long,cha
Wesley13 Wesley13
3年前
C#值类型赋值与引用类型的赋值
 在C中,数据类型大致可以分为两类,一类是值类型,一类是引用类型。初学者往往会被类型之间的相互赋值搞的很迷惑,尤其是引用类型变量的相互赋值。现在举2个例子,来一一说明。值类型变量的赋值: 值类型变量中保存的是实际数据,在赋值的时候只是把数据复制一份,然后赋给另一个变量。例子1:         intvar12;         
Python进阶者 Python进阶者
11个月前
Excel中这日期老是出来00:00:00,怎么用Pandas把这个去除
大家好,我是皮皮。一、前言前几天在Python白银交流群【上海新年人】问了一个Pandas数据筛选的问题。问题如下:这日期老是出来00:00:00,怎么把这个去除。二、实现过程后来【论草莓如何成为冻干莓】给了一个思路和代码如下:pd.toexcel之前把这