내가 학습 파이썬 분해 작업 있었고, 나는이 두 통화를 보여줍니다 생각은 원자되지 않습니다
>>> dis.dis(separate_kv_fast)
2 0 LOAD_FAST 0 (adict)
3 LOAD_ATTR 0 (keys)
6 CALL_FUNCTION 0
9 LOAD_FAST 0 (adict)
12 LOAD_ATTR 1 (values)
15 CALL_FUNCTION 0
18 BUILD_TUPLE 2
21 RETURN_VALUE
>>>
는 여러 옵 코드에서 키와 값을 호출하는 나는 그것이 증명 믿고 원자가 아냐.
의 당신의 bdict = dict(adict)
밖으로 어떻게 작동하는지 살펴 보자
2 0 LOAD_GLOBAL 0 (dict)
3 LOAD_FAST 0 (adict)
6 CALL_FUNCTION 1
9 STORE_FAST 1 (bdict)
LOAD_FAST
는 스택에 adict
에 대한 참조를 푸시합니다. 그런 다음 그 인수와 함께 dict
이라고 부릅니다. 우리가 알지 못하는 것은 dict()
함수가 원자적인 경우입니다.
bdict = adict.copy()
도 유사한 해체를 제공합니다. adict.copy
을 분해 할 수 없습니다.
내가 읽은 모든 내용은 내부 유형이 스레드로부터 안전하다는 것을 알려줍니다. 따라서 사전으로의 단일 함수 호출은 내부적으로 일관성이 있다고 생각합니다. 즉, items()
, copy()
, values()
, keys()
등 keys()
다음 (시리얼 values()
두 통화는 안전 necessarilly 없다. 나도 반복자되어 있지 않습니다.
당신의 단지 items()
?
I을 사용하지 않는 이유가
#!/usr/bin/python
import timeit
import random
D = dict()
for x in xrange(0, 1000):
D[x] = str(x)
def a():
return D.keys(), D.values()
def b():
keys = []
values = []
for k, v in D.items():
keys.append(k)
values.append(v)
return keys, values
def c():
d = D.copy()
return d.keys(), d.values()
def d():
return zip(*D.items())
print timeit.timeit("a()", 'from __main__ import a')
print timeit.timeit("b()", 'from __main__ import b')
print timeit.timeit("c()", 'from __main__ import c')
print timeit.timeit("d()", 'from __main__ import d')
결과 :
6.56165385246
145.151810169
19.9027020931
65.4051799774
,536를 너무 앞서 가서 벤치마킹, 궁금
사본은 금식 한 원자입니다 (dict()를 사용하는 것보다 약간 빠름).
분해 된 버전은 분명히 통찰력을 추가합니다. 내 첫 번째 버전 generate_kv()는 .items() /. iteritems()를 사용합니다. 확실히 더 안전하지만 키퍼와 값을 약간의 속도 저하로 추출하기 위해 반복을 필요로합니다. 그리 많지는 않지만 특히 멀티 프로세싱이나 멀티 스레딩을 사용하여 사전을 생성하는 것을 고려하고 있으므로 궁금합니다. 감사! – clocker
'iteritems()'나는 재진입 성 문제가 있기를 기대한다. 'items()'는 단지 키 값 쌍의 목록을 반환합니다. – rrauenza
'다중 처리 (multiprocessing) '를 사용하면 객체가 프로세스에서 공유되지 않는다는 것을 깨닫게됩니까? 따라서 사전의 동시성은 문제가되지 않습니다. 내가 대답 한 [이 질문] (http://stackoverflow.com/questions/37890199/reduce-execution-time-on-huge-list-generation)에 관심이 있을지도 모른다. 그것은' 다중 처리 '. – rrauenza