얕은 복사와 깊은 복사

GY·2021년 10월 28일
0

[JS] 개념 정리

목록 보기
21/32
post-thumbnail

객체를 프로퍼티 값으로 갖는 객체의 경우

  • 얕은 복사 : 한 단계까지만 복사하는 것
  • 깊은 복사 : 객체에 중첩되어 있는 객체까지 모두 복사하는 것

얕은 복사

const original = {x: {y:1}};
const copy = {...original};
console.log(copy === original) //false
console.log(copy.x === original.x); //true

🥝 Array.slice()

    const players = ['Wes', 'Sarah', 'Ryan', 'Poppy'];

    const team2 = players.slice();
    team2[1]="changed"
    console.log(team2 === players)//false

//['Wes', 'changed', 'Ryan', 'Lux']    ['Wes', 'Sarah', 'Ryan', 'Lux']

slice의 메서드의 인수를 모두 생략하면 원본배열의 복사본을 생성하여 반환한다.
이 때 생성된 복사본은 얕은 복사를 통해 생성된다.

slice는 얕은 복사를 하는데, 왜 원본 배열의 값을 변경하지 않을까?


얕은복사

얕은 복사는 한 단계까지만 복사하는 것을 말하는데, 원본 배열의 참조값을 그대로 복사해온다.

    const players = ['Wes', 'Sarah', 'Ryan', 'Poppy'];

    const team2 = players.slice();
    team2[1]="changed"

    console.log(team2 === players)// false
    console.log(team2[2] === players[2])//true
  • slice는 원본배열과 다른 새로운 배열을 반환하므로, players와 team2는 참조값이 다른 별개의 배열이다. 따라서 team2 === playersfalse이다.

  • 그러나 배열 요소의 참조값은 같다. 즉, 얕은 복사되었다.
    team2[2] === players[2]true이다.



정리

즉, 복사된 배열 자체의 참조값은 새로 생성되었으나,
각 배열 요소의 참조값은 원본 배열요소의 참조값을 그대로 복사해왔기 때문에 (얕은복사) 동일하다.

🥝 [].concat(Array)

🥝 Array.from(Array)

🥝 Object.assign({}, object)

객체를 얕은 복사 하는 경우
const cap2 = Object.assign({}, person, { number: 99});

깊은 복사

🥝 재귀함수를 통한 복사

🥝 JSON.stringify()

🥝 lodash 라이브러리 사용

const _ = require('lodash);
const copy = _.cloneDeep(original);
console.log(copy === original) //false
console.log(copy.x === original.x) //false

공통점

얕은복사와 깊은 복사로 생성된 객체는 모두 원본과는 다른 객체다.
복사본은 원본과 참조값이 다르다.

차이점

차이점은 객체에 중첩되어 있는 객체를 복사할 때 나타난다., 얕은 복사는 객체에 중첩되어 있는 객체의 경우 참조값만 복사하지만,
깊은 복사는 중첩된 객체까지 모두 복사해서 완전한 복사본을 만든다는 것이다.

profile
Why?에서 시작해 How를 찾는 과정을 좋아합니다. 그 고민과 성장의 과정을 꾸준히 기록하고자 합니다.

0개의 댓글