2017-05-30 64 views
0

試圖用numpy優化一段代碼,我想知道這是否是正確的方法。適當的優化一些計算

這裏是計算公式 ,矩陣是下三角。

1

這裏是我的嘗試:

(np.sum(P) - np.trace(P))/np.sum(((t[np.newaxis]).T - t) * P) 

這是好,因爲它可以得到,或者你可以看到一個更有效的方法?

+2

似乎有'p'和'P'。這是打算還是有錯別字? – Divakar

+0

謝謝Divakar,這是一個錯字(編輯)。我擔心部分(t [np.newaxis])。T - t),因爲我認爲它會創建另一個n * n矩陣,這不正確嗎?那麼在這種情況下,簡潔是或不是正確的方法? –

+1

除非您計劃在那裏寫答案,否則請不要推薦代碼複審。如果你在CR上沒有'numpy'相關的代表點,你不知道什麼是合適的。這不是完整的工作副本。不要被「優化」一詞的不同用法所困惑。 – hpaulj

回答

1

瓶頸似乎是分母的計算,看起來像np.einsum應該幫助那裏,因爲我們正在執行元素方式的乘法和和減法。因此,分母可以計算像這樣 -

np.einsum('ij,ij',t[:,None]-t, P) 

時序和驗證 -

In [414]: N = 5000 
    ...: P = np.random.rand(N,N) 
    ...: t = np.random.rand(N) 
    ...: out = (np.sum(P) - np.trace(P))/np.sum(((t[np.newaxis]).T - t) * P) 
    ...: 

# Original method  
In [415]: den1 = np.sum(((t[np.newaxis]).T - t) * P) 

# Proposed method  
In [416]: den2 = np.einsum('ij,ij',t[:,None]-t, P) 

In [417]: np.allclose(den1, den2) 
Out[417]: True 

In [419]: %timeit np.sum(((t[np.newaxis]).T - t) *P) 
10 loops, best of 3: 86.9 ms per loop 

In [420]: %timeit np.einsum('ij,ij',t[:,None]-t, P) 
10 loops, best of 3: 49.7 ms per loop 

對於分子,似乎大部分運行時間都花在np.sum(P)

In [422]: %timeit (np.sum(P) - np.trace(P)) 
100 loops, best of 3: 10.4 ms per loop 

In [423]: %timeit np.sum(P) 
100 loops, best of 3: 10.4 ms per loop 

所以,我們可以讓分子保持原樣。