2012-06-05 3 views
4

numexpr을 사용하여 다음을 어떻게 효과적으로 표현할 수 있습니까? 여기 numexpr에 하위 표현식 캐핑

z = min(x-y, 1.0)/(x+y) 

, x y과 동일한 형상의 약간 큰 NumPy와 배열한다.

즉, 으로 나누기 전에 x-y1.0으로 제한하려고합니다.

numexpr 표현식 (xy은 거대하며 두 번 이상 반복하지 않아도됩니다.)을 사용하여이 작업을 수행하고 싶습니다.

+1

(분 (XY, 1) 유효 NumPy와하지 않기 때문에) 그냥 명확하게하기 위해, 당신은 모자 싶어이 훨씬 예뻐, 빠른 너무 조금 xy를 (x + y)로 나누기 전에 1의 상한선에 씁니다. – DSM

+0

@DSM : 예, 이것은 정확하게 내가하려고하는 것입니다. 나는 그 질문을 편집했다. – NPE

답변

6

아마도 이런 식으로 작동할까요?

In [11]: import numpy as np 
In [12]: import numexpr as ne  
In [13]:  
In [13]: x = np.linspace(0.02, 5.0, 1e7) 
In [14]: y = np.sin(x) 
In [15]:  
In [15]: timeit z0 = ((x-y) - ((x-y) > 1) * (x-y - 1))/(x+y) 
1 loops, best of 3: 1.02 s per loop 
In [16]: timeit z1 = ne.evaluate("((x-y) - ((x-y) > 1.) * ((x-y) - 1.))/(x+y)") 
10 loops, best of 3: 120 ms per loop  
In [17]: timeit z2 = ne.evaluate("((x-y)/(x+y))") 
10 loops, best of 3: 103 ms per loop 

부문 위의 상한에는 패널티가 있지만 너무 나쁘지 않습니다. 불행히도 몇몇 큰 배열을 시도했을 때 segfault가 발생했습니다. : -/

업데이트 :

In [40]: timeit w0 = ne.evaluate("where(x-y>1,1,x-y)/(x+y)") 
10 loops, best of 3: 114 ms per loop