浅拷贝与深拷贝只针对引用类型。而对于值类型谈不上。
- 拷贝就是新建一个空间。将一个对象中的数据拷贝到另一个对象。
- 浅拷贝。对于原数据中的引用类型,会直接把
它的地址拷贝
(这样会和被拷贝对象的引用类型指向同一空间) - 深拷贝。对于原数据中的引用类型,
会开辟新的空间,把它的值进行拷贝
。(这样会和被拷贝对象的引用类型指向不同空间)
- 浅拷贝。对于原数据中的引用类型,会直接把
- 对于第一层来说深拷贝,下层就是浅拷贝。(因为第一层,数据本身就是引用类型,所以会开辟新的空间。但下层,对于其中的引用类型被没有去继续开辟新空间,而是地址的拷贝。)
// object.assign
let obj = {
name: 'fjh',
age: 20,
null: null,
undefined: undefined,
f() {},
arr: [1],
obj: {
name: 'obj'
}
}
// string number null undefined function object object
let new_obj = {};
Object.assign(new_obj, obj);
new_obj.arr = ['改'];
new_obj.obj.name = '改';
console.log(obj, new_obj);
//Array.prototype.concat()
// string number null undefined function object object
let arr = ['fjh', 2, null, undefined, function f() {},
[6], {
name: 'obj'
}
]
let new_arr = [].concat(arr);
arr[5] = ['改'];
arr[6].name = '改';
console.log(arr, new_arr);
// 手写的上述同样的效果。
function clone(obj) {
if (!obj) return obj;
if (typeof obj !== 'object') return obj;
let new_obj = obj instanceof Array ? [] : {};
for (let key in obj) {
new_obj[key] = obj[key];
}
return new_obj;
}
let arr = ['fjh', 2, null, undefined, function f() {},
[6], {
name: 'obj'
}
]
let new_arr = clone(arr);
arr[5] = ['改'];
arr[6].name = '改';
console.log(arr, new_arr);
// JSON.parse(JSON.stringify(obj)) . 对于null、undefined、function的拷贝结果都是null!!!
let arr = ['fjh', 2, null, undefined, function f() {},
[6], {
name: 'obj'
}
]
let new_arr = JSON.parse(JSON.stringify(arr));
arr[5] = ['改'];
arr[6].name = '改';
console.log(arr, new_arr);
function deepClone(obj) {
if (!obj) return obj;
if (typeof obj !== 'object') return obj;
let new_obj = obj instanceof Array ? [] : {};
for (let key in obj) {
new_obj[key] = (typeof obj[key] === 'object') ? deepClone(obj[key]) : obj[key];
}
return new_obj;
}
// string number null undefined function object object
let arr = ['fjh', 2, null, undefined, function f() {},
[6], {
name: 'obj'
}
]
let new_arr = deepClone(arr);
arr[5] = ['改'];
arr[6].name = '改';
console.log(arr, new_arr);