리스트의 얕은 복사(swallow copy)와 깊은 복사(deep copy)
얕은 복사와 깊은 복사란?
얕은 복사는 복사 대상 객체의 주소를 복사하여 새로운 객체를 생성합니다. 원본 객체와 복사된 객체가 같은 메모리 주소를 공유하기 때문에 우너본객체의 변경이 복사된 객체에도 영향을 미칩니다.
깊은 복사는 복사 대상 객체의 모든 내용을 복사하여 완전히 새로운 객체를 생성합니다. 새로운 객체는 원본 객체와 다른 메모리 주소를 가지므로, 원본 객체의 변경이 복사된 객체에 영향을 미치지 않습니다.
예를 들어, 리스트의 경우, 깊은 복사를 수행하면 새로운 리스트 객체가 만들어지고, 리스트 안에 있는 객체들도 새로운 객체로 복사됩니다. 따라서 복사된 리스트 안에 있는 객체들을 수정해도, 원본 리스트 안에 있는 객체들은 수정되지 않습니다.
대입 연산자(=)와 인덱스 슬라이싱을 이용한 복사의 차이
list1 = list2 는 list2의 주소를 list1이 참조하여 같은 메모리를 list1과 list2가 공유하지만,
list1 = list2[:]는 list2의 값을 list1이 복사하여 서로 다른 메모리를 list1과 list2가 참조합니다.
하지만 이는 모두 얕은 복사입니다.
리스트 슬라이싱을 이용한 복사와 깊은 복사의 차이점은 복사된 객체와 원본 객체가 참조하는 객체의 내용이 동일한지 여부입니다.
그렇다면 깊은 복사와 리스트의 인덱스 슬라이싱을 이용한 복사의 차이점은?
깊은 복사는 원본 객체를 재귀적으로 탐색하여 객체 내부에 있는 모든 객체들도 새로운 메모리에 복사합니다. 따라서 복사된 객체와 원본 객체가 참조하는 객체의 내용이 모두 동일하지 않습니다. 예를 들어, 리스트 안에 있는 객체들이 다른 객체일 경우, 깊은 복사를 수행하면 새로운 리스트와 복사된 리스트 안에 있는 객체들은 서로 다른 메모리 주소를 가집니다.
반면에, list[:]를 이용한 얕은 복사는 복사된 객체와 원본 객체가 참조하는 객체의 내용이 동일합니다. 원본 객체를 복사할 때, 리스트의 모든 원소를 새로운 리스트로 복사합니다. 이때 복사된 리스트 안에 있는 원소들은 원본 리스트 안에 있는 원소들과 동일한 객체를 참조합니다. 따라서 복사된 리스트 안에 있는 객체들을 수정하면, 원본 리스트 안에 있는 객체들도 수정됩니다.
잘 이해가 안돼요!
이해가 쉽게 설명하자면,
예를 들어, 깊은 복사는 물체를 완전히 새로 만들어 복사하는 것입니다. 즉, 원본 물체와 복사된 물체가 완전히 별개의 물체입니다. 두 물체는 완전히 다른 내용을 가지고 있으며, 한 쪽을 수정하더라도 다른 쪽에는 영향을 주지 않습니다.
반면에, 얕은 복사는 물체를 새로 만드는 것이 아니라, 원본 물체를 참조하는 새로운 물체를 만드는 것입니다. 예를 들어, 물체 A와 물체 B가 있을 때, B가 A를 참조한다고 생각해보세요. 만약 A를 수정하면, B도 동일한 내용을 가지므로 B도 같이 수정됩니다.
list[:]를 이용한 복사는 리스트를 새로 만들어 복사하는 것입니다. 하지만 리스트 안에 있는 객체들은 복사되지 않고, 원본 리스트 안에 있는 객체들과 동일한 객체를 참조합니다. 따라서 복사된 리스트 안에 있는 객체들을 수정하면, 원본 리스트 안에 있는 객체들도 수정됩니다.
결론적으로, 깊은 복사는 복사된 객체와 원본 객체가 완전히 별개의 객체이며, 얕은 복사와 list[:]를 이용한 복사는 복사된 객체와 원본 객체가 참조하는 객체의 내용이 동일하거나 다를 수 있습니다.
따라서 인덱스 슬라이싱을 이용한 복사에서 2차원 리스트일 때는, 리스트 안에 들어있는 리스트는 복사되지 않고 원본 리스트 안에 있는 리스트를 참조하게 되는 것입니다.
1차원 리스트에서는 인덱스 슬라이싱을 이용한 얕은 복사와 깊은 복사는 같은 결과를 도출합니다. 하지만 2차원 이상의 리스트에서는 깊은 복사와 얕은 복사가 서로 다른 결과를 도출합니다.
chatgpt와 함께 작성했습니다 ^0^