Story 03 깊은 복사와 얕은 복사

유동헌·2021년 9월 26일
0

열혈파이썬_중급

목록 보기
3/8

두 객체의 비교와 복사

객체를 비교할 때 사용할 수 있는 두 가지 연산자를 정리하면 다음과 같다.

v1 == v2 : 변수 v1과 v2가 참조하는 객체의 내용이 같은가?

v1 is v2 : 변수 v1과 v2가 참조하는 객체는 동일 객체인가?
  • 동일한 값을 담고 있는 두 객체를 대상으로 하는 두 연산의 결과는 다음과 같다.
>>> r1 = [1,2,3]
>>> r2 = [1,2,3]
>>> r1 is r2
False
>>> r1 == r2
True
>>> r1 = [1,2,3]
>>> r2 = [1,2,3]
>>> r1 = r2
>>> r1 is r2
True

🌀 참조하는 객체의 내용, 참조하는 객체는 동일 객체

<객체 복사>

>>> r1 = ['john', ('man', 'USA'), [175, 23]]
>>> r2 = list(r1)
>>> r2
['john', ('man', 'USA'), [175, 23]]
>>> type(r2)
<class 'list'>
>>> r1 is r2
False
>>> r1[0] is r2[0]
True
>>> r1[1] is r2[1]
True
>>> r1[2] is r2[2]
True
  • 얕은 복사의 개념

    파이썬이 복사하는 방식

    r1, r2가 복사가 되어 각각 문자열 객체, 튜플 객체, 리스트 객체를 참조한다.

깊은 복사

정리하면 값의 변경이 불가능한 immutable 객체는 얕은 복사를 해도 문제가 되지 않는다. 그러나 값의 변경이 가능한 mutable 객체는 얕은 복사가 문제가 될 수도 있다.

>>> j2021 = ['john', ('man', 'USA'), [175, 23]]
>>> j2022 = list(j2021)
>>> j2022[2][1] += 1
>>> j2021
['john', ('man', 'USA'), [175, 24]]
>>> j2022
['john', ('man', 'USA'), [175, 24]]

john은 해가 지날수록 나이를 먹는다. 그래서 위의 예에서는 2021년도 john의 정보를 기반으로 2022년도의 john의 정보를 만들었다. 그런데 얕은 복사로 인해 2021년의 john 정보도 바뀌어 버렸다. 이렇듯 mutable 객체에 저장된 값들은 변경될 수 있기 때문에 이들에 대해서는 복사 대상을 하나 더 생성하는 깊은 복사라는 것을 해야한다. 즉 다음 객체를 대상으로 복사할 경우,

['john', ('man', 'USA'), [175, 23]]

변경 불가능한 객체와 가능한 객체를 깊은 복사를 통해 안정성과 성능을 모두 만족하는 방법이 된다.

>>> j2021 = ['john', ('man', 'USA'), [175, 23]]
>>> import copy
>>> j2022 = copy.deepcopy(j2021)
>>> j2022[2][1] += 1
>>> j2021
['john', ('man', 'USA'), [175, 23]]
>>> j2022
['john', ('man', 'USA'), [175, 24]]
>>> (j2021[0] is j2021[0]) and (j2021[1] is j2022[1])
True
>>> j2021[2] is j2022[2]
False
  • 위의 결과에서 보이듯이 deepcopy 함수의 호출 결과로 immutable 객체를 대상으로는 얕은 복사가 진행되었고 mutable 객체를 대상으로 깊은 복사가 진행되었다.
profile
지뢰찾기 개발자

0개의 댓글