[JS] 얕은 복사, 깊은 복사 차이 쉽게 이해하기
자바스크립트의 얕은 복사(shallow copy), 깊은 복사(deep copy)에 대해 쉽게 이해해보자.
이에 대해 이해하려면 먼저 자바스크립트의 원시 타입(primitive type)과 객체 타입(object/reference type)에 대해 이해해야 한다.
자바스크립트에서 데이터 타입은 크게 원시 타입과 객체 타입으로 나뉜다.
원시 타입에는 Number, BigInt, String, Boolean, Null, Undefined, Symbol 7개의 타입이 있고,
그 외 모든 데이터는 객체 타입이다.
원시 값을 변수에 할당하면 변수(확보된 메모리 공간)에는 실제 값이 저장된다.
반면에, 객체를 변수에 할당하면 변수(확보된 메모리 공간)에는 참조 값(메모리 주소)이 저장된다.
이를 코드와 그림으로 나타내면 다음과 같다.
객체는 참조 값을 복사하기 때문에 let obj2 = obj1와 같이 객체를 복사할 경우 얕은 복사가 일어난다.
얕은 복사(shallow copy)는 원본 객체는 하나인 상태에서, 참조 값만 복사한다.
깊은 복사(deep copy)는 원시 값처럼 완전한 복사본을 만든다. 깊은 복사는 lodash의 cloneDeep을 사용해 수행 가능하다.
let obj1 = { name: 'choar', age: 20 };
let obj2 = obj1;
console.log(obj1); // { name: 'choar', age: 20 }
console.log(obj2); // { name: 'choar', age: 20 }
obj1.name = 'hi';
console.log(obj1); // { name: 'hi', age: 20 }
console.log(obj2); // { name: 'hi', age: 20 }
// 얕은 복사로 인해 obj1, obj2가 가리키는 객체는 같다.
// lodash의 cloneDeep을 사용한 깊은 복사
// "npm install lodash"로 lodash를 설치한 후, Node.js 환경에서 실행
const _ = require('lodash');
let obj3 = _.cloneDeep(obj1);
obj3.name = 'hello';
console.log(obj1); // { name: 'hi', age: 20 }
console.log(obj3); // { name: 'hello', age: 20 }
추가로, 객체의 경우 변수가 참조 값을 저장하고 있기 때문에 const로 선언해도 내부 프로퍼티 값 변경이 가능한 것이다. (참조 값은 변경 불가, 참조 값이 가리키는 객체는 변경 가능)
References
모던 자바스크립트 Deep Dive (Chapter 11)
https://developer.mozilla.org/ko/docs/Web/JavaScript/Data_structures
'프로그래밍 > JavaScript' 카테고리의 다른 글
[JS] 객체 프로퍼티 접근법과 식별자 네이밍 규칙 (0) | 2022.04.26 |
---|---|
[JS] 이벤트 객체의 target, currentTarget 차이 (0) | 2022.04.19 |
[JS] 이벤트 위임을 활용한 Event Listener 중복 문제 해결 (0) | 2022.03.12 |
[JS] 단축 평가(Short-Circuit Evaluation) 쉽게 이해하기 | &&, ||, 연산자 우선순위 (0) | 2022.03.07 |
[자바스크립트] class vs object, 객체지향 언어 클래스 정리 (0) | 2021.03.22 |