객체는 다른 객체를 참조 할 수 있는데, 이럴경우 깊은복사인가, 얕은 복사인가에 따라 결과값이 달라질 수 있다.
복사한다는 것은 기존 객체와 같은 값들을 가진 새로운 객체를 만든다는 것
객체들은 멤버를 가지고 있고, 그 멤버들은 값일수도, 참조일수도 있다.
이 객체들이 가진 값 형식과 참조 형식의 복제방식에 따라 얕은복사와 깊은복사의 개념이 나뉜다.
객체가 가진 멤버들의 값을 새로운 객체로 복사하는데 만약 객체가 참조타입의 멤버를 가지고 있다면, 참조값만 복사가 된다.
바로 아래 단계의 값만 복사하는 방법
var user = {
name: 'jaeman'
gender: 'male'
}
var user2 = {user}
++ Object.assign을 이용하는 경우
const obj = {a: 1, b: 2};
const target = {c: 3};
const copiedObj = Object.assign(target, obj);
console.log(copiedObj); //{c: 3, a: 1, b: 2}
Object.assign으로는 객체 내부에 존재하는 객체는 완전한 복사가 이루어지지 않는다.
const original = {
a: 1,
b: 2,
c: {
d: 3
}
};
const copied = {...original};
original.a = 1000;
original.c.d= 3000;
console.log(copied.a); // 1
console.log(copied.c.d); // 3000
위와 마찬가지로 프로퍼티로 객체가 있으면 참조를 해버린다.
내부의 모든 값들을 하나하나 찾아서 전부 복사하는 방법
중첩된 객체에서 참조형 데이터가 저장된 프로퍼티를 복사할 때 그 주솟값만 복사한다는 의미
var copyObjectDeep = function (target) {
var result = {};
if (typeof target === 'object' && target !== null) {
for (var prop in target) {
result[prop] = copyObjectDeep(target[prop]);
}
} else {
result = target;
}
return result;
};
// type검사를 object로 해놓고 null이 아닌걸 찾는 이유는
// typeof null은 object이기 때문, 자바스크립트의 오류인듯하다.
var obj = {
a: 1,
b: {
c: null,
d: [1,2]
}
}
var obj2 = copyObjectDeep(obj);
obj2.a = 3;
obj2.b.c = 4;
obj.b.d[1] = 3;
console.log(obj)
console.log(obj2)
var copyObjectViaJSON = function(target) {
return JSON.parse(JSON.stringify(target));
};
var obj = {
a: 1,
b: {
c: null,
d: [1,2],
func1: function() { console.log(3); }
},
func2: function() { console.log(4);}
};
var obj2 = copyObjectViaJSON(obj);
obj2.a = 3;
obj2.b.c = 4;
obj.b.d[1] = 3;
console.log(obj);
console.log(obj2)
다만 이 방법으로는 메소드나 _proto_
getter/setter등은 변경되지 않는다