[Python] [{...}] * 10 주의점 Develop Tip

오랫만에 파이썬 관련 블로깅을 해 봅니다.
항상 돌리다가 부딪히는 문제는 심히 마음이 아프지만
하나 하나 또 배운다는 느낌입니다.

아래의 간단한 코드를 보겠습니다.

cxt = []
num = 10
for _ in range(num):
    cxt.append({'foo': 1})
print(cxt)

10개 만큼의 {'foo': 1} 이라는 기본 딕셔너리를 가진
어레이를 만들어 거기에 무언가 작업을 해보려는 것이었습니다.

그런데 좀 더 'Pythonic' 하게 만들어 보기 위하여

num = 10
cxt = [{'foo': 1}] * num
print(cxt)

라고 했습니다.

우와 보기도 훨씬 깔끔하구나 하고 생각했습니다.

둘 다 같은 결과가 찍힙니다.

[{'foo': 1}, {'foo': 1}, {'foo': 1}, {'foo': 1}, {'foo': 1}, {'foo': 1}, {'foo': 1}, {'foo': 1}, {'foo': 1}, {'foo': 1}]

그런데 두번 째 방법에서

10개의 리스트 중 첫번째 딕셔너리만 1을 추가하기 위하여

cxt[0]['foo'] += 1

라고 한 다음
cxt를 출력해 보면

[{'foo': 2}, {'foo': 2}, {'foo': 2}, {'foo': 2}, {'foo': 2}, {'foo': 2}, {'foo': 2}, {'foo': 2}, {'foo': 2}, {'foo': 2}]

오잉!!

디버깅하다가 발견한 사실!!

아하!

두번째 방법으로 만든 것은, 위에 개별로 보이는 {'foo': 1} 은 
실제로 하나의 사전 객체를 가리키고 있었다는 사실.

따라서 실제 코드는 첫번째 처럼 작성해야 합니다.


어느 분께는 도움이 되셨기를...


덧글

  • 지나가다 2018/03/16 17:49 # 삭제 답글

    [{'foo' : 1} for _ in range(10)]
  • 지훈현서아빠 2018/03/16 17:58 #

    오 내포 리스트로 하면 훨씬 좋군요..
    고맙습니다. ^^
  • 서치 2018/03/17 12:41 # 삭제 답글

    import copy
    ctx = [copy.deeppcopy({“foo”: 1})] * num
  • 지훈현서아빠 2018/03/17 16:16 #

    안타깝게도 위에 해 주신 예문은 동일한 객체를 가리킵니다..
댓글 입력 영역

구글애드텍스트