<백준 문자열 - 1157번 단어공부> 에서 해결하지 못했던 의문점이 드디어 풀렸다.
word 라는 리스트를 remove_word = word 를 사용해 복사해 두고, remove_word에서 값을 제거했는데 word에서도 값이 계속 함께 지워졌던...
결국 그 오류의 원인을 알지 못하고 set 형을 사용하는 걸로 해결했는데, 드디어 답을 찾았다.
remove_word = word 와 같이 복사를 하면 내용이 아니라 주소값이 복사가 되어서 둘은 같은 배열을 가리키게 된다.
이를 해결하기 위해서는 깊은 복사를 이용하거나 반복문으로 하나하나 값을 가져와도 된다는 답을 얻었다.
깊은 복사와 얕은 복사를 알아보기 이전에 우선 mutable과 immutable 객체에 대한 이해가 필요하다.
- mutable: 상태를 변경할 수 있는 객체
- immutable: 상태를 변경할 수 없는 객체
mutable | immutable |
list | bool |
set | int |
dict | float |
사용자가 작성한 대부분dml Class | tuple |
str | |
frozenset |
a = [1,2,3,4,5]
print(a[0],end="\n\n")
a[0] = 0
print(a[0])
a = "abc"
print(a[0],end="\n\n")
a[0] = "d"
print(a[0])
#얕은 복사(shallow copy)
- 변수(값)을 복사하는 것이 아니라 원본과 복사본이 동일한 메모리 주소을 가리킨다.
- immutable 객체는 얕은 복사를 해도 그 후 값을 변경하면 무조건 메모리 주소가 변경된다. 따라서 복사본과 원본 중 하나에서 값을 변경해도 다른 하나는 변하지 않는다.
- mutable 객체는 얕은 복사를 한 후 값을 변경할 때 메모리 주소가 변하지 않아 복사본과 원본이 모두 함께 변경된다.
1. 대입 연산자 '=' 이용
<immutable>
num1 = 10
num2 = num1
num1 = 4
print(num1) #4
print(num2) #10
<mutable>
word = [1, 2, 3, 4, 5]
remove_word = word
print(word) #[1, 2, 3, 4, 5]
print(remove_word) #[1, 2, 3, 4, 5]
print(id(word)) #2608498067072
print(id(remove_word)) #2608498067072
2. '[:]' 슬라이싱 이용
arr1 = [1, 2, 3, 4, [5, 6, 7, 8]]
arr2 = arr1[:]
print(arr1) #[1, 2, 3, 4, [5, 6, 7, 8]]
print(arr2) #[1, 2, 3, 4, [5, 6, 7, 8]]
arr1[0] = 6
print(arr1) #[6, 2, 3, 4, [5, 6, 7, 8]]
print(arr2) #[1, 2, 3, 4, [5, 6, 7, 8]]
arr1[4].append(9)
print(arr1) #[6, 2, 3, 4, [5, 6, 7, 8, 9]]
print(arr2) #[1, 2, 3, 4, [5, 6, 7, 8, 9]]
3. copy 메서드 이용
arr1 = [1, 2, 3, 4, [5,6]]
arr2 = arr1.copy()
print(arr1) #[1, 2, 3, 4, [5, 6]]
print(arr2) #[1, 2, 3, 4, [5, 6]]
arr1[0] = 6
print(arr1) #[6, 2, 3, 4, [5, 6]]
print(arr2) #[1, 2, 3, 4, [5, 6]]
arr1[4].append(7)
print(arr1) #[6, 2, 3, 4, [5, 6, 7]]
print(arr2) #[1, 2, 3, 4, [5, 6, 7]]
import copy
arr1 = [1, 2, 3, 4, [5,6]]
arr2 = copy.copy(arr1)
print(arr1) #[1, 2, 3, 4, [5, 6]]
print(arr2)
arr1[0] = 6
print(arr1) #[6, 2, 3, 4, [5, 6]]
print(arr2) #[1, 2, 3, 4, [5, 6]]
arr1[4].append(7)
print(arr1) #[6, 2, 3, 4, [5, 6, 7]]
print(arr2) #[1, 2, 3, 4, [5, 6, 7]]
4. copy 모듈의 copy 함수 이용
import copy
arr1 = [1, 2, 3, 4, [5,6]]
arr2 = copy.copy(arr1)
print(arr1) #[1, 2, 3, 4, [5, 6]]
print(arr2) #[1, 2, 3, 4, [5, 6]]
arr1[0] = 6
print(arr1) #[6, 2, 3, 4, [5, 6]]
print(arr2) #[1, 2, 3, 4, [5, 6]]
arr1[4].append(7)
print(arr1) #[6, 2, 3, 4, [5, 6, 7]]
print(arr2) #[1, 2, 3, 4, [5, 6, 7]]
#깊은 복사(deep copy)
- mutable 내부에 있는 객체들까지 다 새롭게 복사할 수 있다.
- 복사한 후 원본이나 복사본 중 하나를 변경해도 다른 한 값은 변하지 않는다.
import copy
arr1 = [1, 2, 3, 4, [5,6]]
arr2 = copy.deepcopy(arr1)
print(arr1)
print(arr2, end="\n\n\n\n")
arr1[0] = 6
print(arr1)
print(arr2, end="\n\n\n\n")
arr1[4].append(7)
print(arr1)
print(arr2)
'파이썬(PYTHON) > 개념정리' 카테고리의 다른 글
[파이썬(Python)] all, any (0) | 2022.10.22 |
---|---|
[파이썬(Python)] 리스트 내포 반복문, 조건문 (1) | 2022.10.08 |
[파이썬(Python)] 크롤링 (0) | 2022.07.31 |
[파이썬(Python)] 간단한 Quiz (0) | 2022.07.30 |
[파이썬(Python)] 정규표현식 (0) | 2022.07.30 |