2012-10-12 5 views
0
>>> import Queue 
>>> q = Queue.PriorityQueue() 
>>> a = (1, {'item': 'value'}) 
>>> q.put(a) 
>>> q.queue 
[(1, {'item': 'value'})] 
>>> a[1]['count'] = 1 
>>> q.queue 
[(1, {'count': 1, 'item': 'value'})] 
>>> q.get() 
(1, {'count': 1, 'item': 'value'}) 

추가 후 'a'값을 변경하면 대기열의 값이 변경되는 이유는 무엇입니까? 튜플 자체는 변경 가능하지 않지만 내부에있는 사전은 변경할 수 있습니다. 그러나 큐가 왜 변경되어야 하는지를 이해할 수 없습니까?우선 순위 대기열 및 Mutability

+0

확인'q.get는() A'를 그리고 당신은 볼 수 그들이 모두 * 같은 튜플에 포인트 *. – satoru

+0

'큐'에 저장되는 튜플에 대한 참조이지 복사본이 아닙니다. – satoru

+0

'q.put (a)'를 실행하면 참조로'a'를'q'로 전달하고'a'는 변경할 수 있습니다. – iMom0

답변

2

파이썬에서는 객체가 참조로 전달됩니다. 일부 객체는 값 (문자열 및 정수 등)으로 전달되는 것처럼 보일 수 있지만 이러한 객체는 변경할 수 없기 때문에 (예 : 정수 객체 1의 값을 변경할 수 없음)

그래서 사전을 대기열에 넣으면 사본이 아닌 다른 다른 끝으로 튀어 나올 실제 사전입니다.

복사본을 원할 경우 사전의 copy() 메서드를 사용할 수 있지만 사전의 얕은 복사본 만 제공한다는 점에 유의하십시오. 복사본의 키와 값은 동일한 개체가 될 수 있으며 변경할 수 있습니다 .

1

파이썬에서는 개체가 '참조로'전달되지도 않고 '값으로'전달되지 않습니다.

예를 들어 a이라는 이름은 (1, {'item': 'value'})이라는 개체에 바인딩됩니다.

이름 q은 큐 개체에 바인딩됩니다. q.put(a)를 호출하면

는 이름 a이있다 바인딩되는 개체는 이름 aq[0]가 같은 객체를 참조하도록 이름 q이 바인딩되는 객체를 "넣어". 따라서 해당 개체를 수정할 때 aq[0]이 바인딩 된 개체가 수정됩니다 (동일한 개체에 바인딩되어 있기 때문에).

둘째, 튜플은 변경 불가능하지만 변경할 수 없음을 의미하지는 않습니다. '컨테이너'는 변경 불가능하고 변경 될 수 없지만 변경 가능한 객체를 포함 할 수 있으므로 내용이 변경 될 수 있습니다. 여기

매우 유용하고 명확한 기사 : https://jeffknupp.com/blog/2012/11/13/is-python-callbyvalue-or-callbyreference-neither/