python3 변수를 복사하기

>>> for j in range(10):
...     random.seed()
...     for i in range(6):
...         num.append(random.randint(0,9))
...     num_col.append(num)
...     num.clear()
...
>>> num_col
[[], [], [], [], [], [], [], [], [], []]

위의 소스는 랜덤값 6개를 만들어 리스트를 만들고 그 값을 num_col 리스트에 추가 합니다. 하지만 결과는 아무값도 들어가지 않습니다. 왜냐 하면 그 아래 num.clear() 때문입니다. 

프로그램을 배우신 분이라면 당연히 아시겠지만....num_col 에는 num 의 값이 들어가는게 아니라 주소값이 들어 가기 때문입니다.

>

원하는 결과를 얻는 방법은 2가지가 있습니다. 

for j in range(10):
    random.seed()
    for i in range(6):
        num.append(random.randint(0,9))
    num_col.append(num)
    num=[]

위와 같이 num.clear() 대신 num=[] 같이 새로운 값을 할당해 버리면 됩니다. 그러면 새로운 객체가 생성되고 num 의 주소값이 바뀌기 때문에 저 위와 같은 문제가 없습니다. 

>

또 한가지 방법이 copy 명령을 써서 변수를 복사 하는 겁니다. 

import random
import copy

num=[]
num_col=[]

for j in range(10):
    random.seed()
    for i in range(6):
        num.append(random.randint(0,9))
    num_col.append(copy.copy(num))
    num.clear()

이렇게 하면 새로운 객체를 생성해서 값을 모두 복사해서 num_col 에 추가 하기 때문에 문제가 없습니다. 

copy 대신 deepcopy 도 있는데 위와 같은 경우는 어느 걸 써도 차이가 없습니다. 이를 간단히 테스트를 해 보면....

>>> num1=[1,2,3,4,5]
>>> num2 = copy.copy(num1)
>>> id(num1[0])
9468256
>>> id(num2[0])
9468256
>>> num2=copy.deepcopy(num1)
>>> id(num1[0])
9468256
>>> id(num2[0])
9468256

copy나 deepcopy 를 쓰면 num1 과 num2 의 id 값은 달라지지만 num1[0] 과 num2[0] 의 id 값은  copy를 하나 deepcopy 를 하나 동일합니다. 

 하지만 아래와 같은 경우는 차이가 있습니다.

>>> num1=[[1,2,3]]
>>> num2 = copy.copy(num1)
>>> id(num1[0])
140714158508608
>>> id(num2[0])
140714158508608
>>> num2 = copy.deepcopy(num1)
>>> id(num1[0])
140714158508608
>>> id(num2[0])
140714150150784

num1[0] 와 num2[0] 의 id 값을 비교해 보면 copy 와 deepcopy 했을때의 차이를 보실 수 있습니다.

 

결론적으로 말하자면....보통은 copy 를 써도 되지만, 완전한 복사를 하려면 deepcopy 를 쓰는게 확실하다는 겁니다. 


댓글