2017-11-24 13 views
2

私は同じ形の2つの3Dブール値の配列を持っています(たとえば、(512,512,512)としましょう)。 1つの配列のTrue領域が完全に2番目の配列に含まれているかどうか確認したいと思います。高速ndarrayブール代数

は、今私が思い付くした最高のは、次のとおりです。

np.all((A * B) == A) 

これを行うにはより高速な方法はありますか?残念ながら、これは内部のループの中に入ります。私はさらに最適化することができませんので、より多くの方がこれをよりよく削ります。

答えて

2

アプローチ#1:彼らはブール配列の場合、AND-ingは乗算よりも良いかもしれません -

((A & B) == A).all() 

アプローチ#2:真の値のカウントと別 -

np.count_nonzero(A & B) == np.count_nonzero(A) 

ランタイムテスト -

In [225]: A = np.random.rand(512,512,512)>0.5 
    ...: B = np.random.rand(512,512,512)>0.5 

In [226]: %timeit np.all((A * B) == A) 
    ...: %timeit ((A & B) == A).all() 
    ...: %timeit np.count_nonzero(A & B) == np.count_nonzero(A) 
10 loops, best of 3: 170 ms per loop 
10 loops, best of 3: 169 ms per loop 
10 loops, best of 3: 57.7 ms per loop 

アプローチ#3:は基本的に対応するBがされていないため、任意のA真があるかどう探しnumbaレベルで短絡する - このShort-circuiting

from numba import njit 

@njit 
def numba_app(a, b): 
    l = len(a) 
    out = True 
    for i in range(l): 
     if a[i] & ~b[i]: 
      out = False 
      break 
    return out 

out = numba_app(A.ravel(), B.ravel()) 

タイミングメソッドはデータに依存します。

+0

クール、アプローチ#2は実際に交差点を確認していますか?実際は私の場合ではありませんが、2つの配列の穴数が同じであれば、一致しない場合でも真と評価できます。 – filippo

+0

@filippo異なる位置に同じ数の穴がある場合、 'A&B'は' A'のTrue値よりもTrue値が小さくなります。そういうわけで、それは機能します。重要なのは、私がA&BのTruesを数えていることです。たぶんあなたはそこで混乱しています。 – Divakar

+0

ええ、そうですよ!それはおそらく休憩を取るとコーヒーを持っている時間です...ありがとう – filippo

関連する問題