关于对象,对象数组,数组,数组对象直接拷贝、浅拷贝、深拷贝问题的总结
2018-03-16 14:49
344 查看
1、对象、对象的数组或者对象的对象(两者同理)
直接拷贝:将一个对象直接复制(拷贝)给另外一个对象,当一个对象改变时,则另一个对象则也会被改变,因为两个对象总的变量指向的是内存中同一位置。
举例说明:
let obj1 = {id: 1,value: 1,steps:[]};
let obj2 = obj1;
obj2.id = 2;
console.log(obj1);//{id: 2,value:1}
obj1.value = 2;
console.log(obj2);//{id: 2,value:2}
对象浅拷贝:只拷贝对象的一层,仅仅拷贝对象本身(包括对象中的基本变量),而不拷贝对象包含的引用指向的对象;浅拷贝的方法有Jquery提供的$.extend(); 或者ES6+提供的Object.assign(target,source)(这个使用的方法);
let obj1 = {id: 1,value: 1,steps:[]};
let obj2=Object.assign({},obj1) 或者
let obj2 = {};
Object.assign(obj2,obj1)
//改变对象中的基本变量,两个对象中的值没有改变
obj1.id = 2;
console.log(obj2);//{id: 1,value: 1,steps:[]}
obj2.value = 2;
console.log(obj2) ;//{id: 1,value:2,steps:[]};
//当改变对象中的数组时,两个对象值都会被修改,因为他们指向同一内存位置
obj1.steps = [1,2,3];
console.log(obj2.steps); //[1,2,3] ;
或者
let steps = obj1.steps;//注意数组的拷贝问题,下面会细说
steps[0] = 2; //steps = [3,3,3](这样赋值表现形式也会不一样喔,这个是数组拷贝问题,steps指向了一个新内存地址)
console.log(obj1.steps); //[2,2,3]
console.log(obj2.steps);//[2,2,3]
对象深拷贝:将拷贝对象所引用的对象全部复制一遍,所有引用指向了一个新的内存地址;实现方法:$.extend([deep],target,object1,object2[,objectN])
举例说明:
let obj1 = {id: 1,value:1,steps:[]};
let obj2 = $.extend(true,{},obj1);
obj1.steps = [1,2,3];
console.log(obj2);//{id:1,value:1,steps:[1,2,3]}
2、数组、数组对象的浅拷贝,深拷贝;(原理与对象拷贝一样)
浅拷贝:将数组值直接赋值给另外一个数组;
举例说明:简单的数组
let a = [1,2,3,4];
let b = a;
a[4] = 5;
console.log(b);//[1,2,3,4,5]
b.pop();
console.log(a);[1,2,3,4];
//定义一个数组对象
let a = [{id: 1,value:1}];
let b = a;
let node = a[0];//数组的对象被修改,则数组也会被修改,对象的拷贝请看上面如何操作
node.id = 2,
node.value = 2;
console.log(a); //[{id: 2,value: 2}]
//另外一直情况请思考
let a = [{id:1,value: 2}];
4000
let b = [];
for(let node of a){
b.push(node);
}
a[0].id = 2;
a[0].value = 2;
console.log(b);//b的值是多少?
深拷贝:定义一个新数组,将需要复制的数组成员重复赋值给另外一个数组;
举例说明:简单数组的拷贝,可以用数组的操作方法实现拷贝,.slice() .concat();
let a = [1, 2 ,3, 4];
let b = [];
for(let node of a) {
b.push(node);
}//或者 b = a.slice(a) b = a.concat();
a.push(5);
console.log(a);//[1,2,3,4,5]
console.log(b);//[1,2,3,4];//a b 指向不同的新内存位置,所以,如果a 或者b 改变不会影响对方;
//数组对象的拷贝不能使用上面的方法
let a = [{id: 1,value:1}];
let b = [];
for(let node of a) {
let node2 = $.extend(true,{},node);/这里使用对象深拷贝,浅拷贝不起作用
b.push(node2);
}
a[0].id = 2;
a[0].value = 2;
console.log(b); //[{id: 1,value:2}]3、结束语:
对象数组,数组对象在实际应用中非常有用;有问题欢迎吐槽,记得点赞哦。
直接拷贝:将一个对象直接复制(拷贝)给另外一个对象,当一个对象改变时,则另一个对象则也会被改变,因为两个对象总的变量指向的是内存中同一位置。
举例说明:
let obj1 = {id: 1,value: 1,steps:[]};
let obj2 = obj1;
obj2.id = 2;
console.log(obj1);//{id: 2,value:1}
obj1.value = 2;
console.log(obj2);//{id: 2,value:2}
对象浅拷贝:只拷贝对象的一层,仅仅拷贝对象本身(包括对象中的基本变量),而不拷贝对象包含的引用指向的对象;浅拷贝的方法有Jquery提供的$.extend(); 或者ES6+提供的Object.assign(target,source)(这个使用的方法);
let obj1 = {id: 1,value: 1,steps:[]};
let obj2=Object.assign({},obj1) 或者
let obj2 = {};
Object.assign(obj2,obj1)
//改变对象中的基本变量,两个对象中的值没有改变
obj1.id = 2;
console.log(obj2);//{id: 1,value: 1,steps:[]}
obj2.value = 2;
console.log(obj2) ;//{id: 1,value:2,steps:[]};
//当改变对象中的数组时,两个对象值都会被修改,因为他们指向同一内存位置
obj1.steps = [1,2,3];
console.log(obj2.steps); //[1,2,3] ;
或者
let steps = obj1.steps;//注意数组的拷贝问题,下面会细说
steps[0] = 2; //steps = [3,3,3](这样赋值表现形式也会不一样喔,这个是数组拷贝问题,steps指向了一个新内存地址)
console.log(obj1.steps); //[2,2,3]
console.log(obj2.steps);//[2,2,3]
对象深拷贝:将拷贝对象所引用的对象全部复制一遍,所有引用指向了一个新的内存地址;实现方法:$.extend([deep],target,object1,object2[,objectN])
举例说明:
let obj1 = {id: 1,value:1,steps:[]};
let obj2 = $.extend(true,{},obj1);
obj1.steps = [1,2,3];
console.log(obj2);//{id:1,value:1,steps:[1,2,3]}
2、数组、数组对象的浅拷贝,深拷贝;(原理与对象拷贝一样)
浅拷贝:将数组值直接赋值给另外一个数组;
举例说明:简单的数组
let a = [1,2,3,4];
let b = a;
a[4] = 5;
console.log(b);//[1,2,3,4,5]
b.pop();
console.log(a);[1,2,3,4];
//定义一个数组对象
let a = [{id: 1,value:1}];
let b = a;
let node = a[0];//数组的对象被修改,则数组也会被修改,对象的拷贝请看上面如何操作
node.id = 2,
node.value = 2;
console.log(a); //[{id: 2,value: 2}]
//另外一直情况请思考
let a = [{id:1,value: 2}];
4000
let b = [];
for(let node of a){
b.push(node);
}
a[0].id = 2;
a[0].value = 2;
console.log(b);//b的值是多少?
深拷贝:定义一个新数组,将需要复制的数组成员重复赋值给另外一个数组;
举例说明:简单数组的拷贝,可以用数组的操作方法实现拷贝,.slice() .concat();
let a = [1, 2 ,3, 4];
let b = [];
for(let node of a) {
b.push(node);
}//或者 b = a.slice(a) b = a.concat();
a.push(5);
console.log(a);//[1,2,3,4,5]
console.log(b);//[1,2,3,4];//a b 指向不同的新内存位置,所以,如果a 或者b 改变不会影响对方;
//数组对象的拷贝不能使用上面的方法
let a = [{id: 1,value:1}];
let b = [];
for(let node of a) {
let node2 = $.extend(true,{},node);/这里使用对象深拷贝,浅拷贝不起作用
b.push(node2);
}
a[0].id = 2;
a[0].value = 2;
console.log(b); //[{id: 1,value:2}]3、结束语:
对象数组,数组对象在实际应用中非常有用;有问题欢迎吐槽,记得点赞哦。
相关文章推荐
- 关于对象深拷贝和数组去重的问题...
- javascript关于对象深拷贝和数组去重的问题...
- java笔记:关于复杂数据存储的问题--基础篇:数组以及浅拷贝与深拷贝的问题(下)
- 关于OC对象拷贝的问题
- 关于数组的复制问题------浅拷贝,深拷贝
- 关于可变数组或字典的拷贝内容的问题(非拷贝指针)
- java笔记:关于复杂数据存储的问题--基础篇:数组以及浅拷贝与深拷贝的问题(上)
- 关于PHP在数组对象与JSON数据之间的转换问题(编码问题)
- 关于 JavaScript 中一个小细节问题 (在控制台中直接 {Name:'王尼玛',Age:20} 对象报错问题)
- 01背包问题 总结关于为什么01背包优化成1维数组后,内层循环是逆序的?
- 【C++总结】关于函数返回对象析构的问题
- 关于ajax对象一些常用属性、事件和方法大小写比较常见的问题总结
- 关于复杂数据存储的问题--基础篇:数组以及浅拷贝与深拷贝的问题(上)
- 关于深拷贝(含数组对象)
- 关于不正常地定义参数对象。提供了不一致或不完整的信息或者MySQL server has gone away的问题总结
- ActionScript3中关于数组深浅拷贝的问题
- 关于String s1 = new String("abc") 创建一个对象问题和Java常量池总结
- 关于直接比较两个对象是否相等或则说List集合里是否包含某个对象的问题
- java笔记:关于复杂数据存储的问题--基础篇:数组以及浅拷贝与深拷贝的问题(上)
- 关于OC对象拷贝的问题