2014-11-06 2 views
7

이러한 숫자를 임의로 선택했지만 이러한 결과는 일관성이있는 것처럼 보입니다. float 지수는 정수보다 25 % -50 % 빠릅니다. 어떻게 다르게 처리됩니까?정수 지수에 numpy.power가 느린 이유는 무엇입니까?

In [209]: %timeit -n 100000 -r 100 np.power(3.71242, 7) 
100000 loops, best of 100: 3.45 µs per loop 

In [210]: %timeit -n 100000 -r 100 np.power(3.71242, 7.0) 
100000 loops, best of 100: 1.98 µs per loop 
+0

만약 내가 추측해야만한다면 numpy는 float을 기대하지만 int를 받아 변환해야합니다. –

+0

@JeffMercado 흥미로운 아이디어 ---하지만 "% timeit -n 100000 -r 10 if (type (2) == int) : float (2)" ==> "100000 루프 당 최고 10 : 571ns " – DilithiumMatrix

+0

플로트 지수가 로그를 사용하는 동안 int 지수가 실제 곱셈을 일으킨다 고 생각합니다. –

답변

13

np.poweruniversal function이다 (ufunc). 이 함수는 다양한 데이터 유형을 가진 스칼라와 배열에서 사용될 수 있지만 먼저 적합한 출력 값을 생성하는 데 사용할 내부 루프를 결정할 수 있도록 입력 값 유형을 확인해야합니다.

입력 유형이 ufunc의 미리 정의 된 루프에 매핑되지 않으면 ufunc는 cast the input values to suitable types을 시도합니다 (달리 언급하지 않는 한). 이 입력 값의 확인 및 변환에는 성능 비용이 관련되어있어서 질문에서 관찰 된 타이밍을 설명합니다.

ufunc의 types 속성은 입력 데이터 유형을 출력 데이터 유형에 매핑하는 방법을 보여줍니다. 다음은 np.power에 대한 매핑의 목록은 다음과 같습니다

>>> np.power.types # 'input input -> output' 
['bb->b', 'BB->B', 'hh->h', 'HH->H', 'ii->i', 'II->I', 'll->l', 'LL->L', 'qq->q', 
'QQ->Q', 'ee->e', 'ff->f', 'dd->d', 'gg->g', 'FF->F', 'DD->D', 'GG->G', 'OO->O'] 

부동 소수점 숫자를 문자 코드 'g'에 속하는, 파이썬 정수 'l'에 속한다. 이 문자 코드의 전체 목록은 here입니다.

이 ufunc의 경우 두 입력 값의 데이터 유형이 같아야합니다. 예를 들어, floatint 입력 데이터 유형의 혼합에 대한 매핑이 없습니다.

그러나 여전히 np.power 개의 데이터 유형에 적절한 데이터 유형으로 값을 형변환 할 수 있습니다. floatint를 들어, float64 숫자가 반환됩니다

>>> np.power(3.71242, 7).dtype 
dtype('float64') 

당신이 float64 문자 코드 g에 매핑되는 경우에만 입력이 다른 두 g 값이라고 볼 수 있습니다 위 : 'gg->g'.

그래서 뒤에서 np.power(3.71242, 7)은 파이썬 float과 파이썬 int을 가져 와서 안전하게 재구성 할 수있는 유형과 유형을 결정해야했습니다. int 값은 float 유형 g으로 안전하게 승격되었습니다. 그런 다음 ufunc는 실행할 루프를 알고 다른 g 값을 반환했습니다.

이러한 이유로 입력 데이터 유형을 혼합하지 않으면 np.power의 성능이 향상됩니다.