mxn行列の場合、列のすべてのペア ( nxn )の相互情報を計算する最適な (最速の) 方法は何ですか?
相互情報とは、次のことを意味します。
I(X, Y) = H(X) + H(Y) - H(X,Y)
ここで、H(X)はXのシャノン エントロピーを表します。
現在、私は and を使用np.histogram2d
しnp.histogram
て、関節(X、Y)と個々の(X または Y)の数を計算しています。特定の行列A
(たとえば、250000 X 1000 の float 行列) に対して、ネストされたfor
ループを実行しています。
n = A.shape[1]
for ix = arange(n)
for jx = arange(ix+1,n):
matMI[ix,jx]= calc_MI(A[:,ix],A[:,jx])
確かにこれを行うためのより良い/より速い方法があるに違いありませんか?
余談ですが、配列の列に対するマッピング関数 (列方向または行方向の操作) も探しましたが、まだ適切な一般的な答えは見つかりませんでした。
Wikiページの規則に従って、私の完全な実装を次に示します。
import numpy as np
def calc_MI(X,Y,bins):
c_XY = np.histogram2d(X,Y,bins)[0]
c_X = np.histogram(X,bins)[0]
c_Y = np.histogram(Y,bins)[0]
H_X = shan_entropy(c_X)
H_Y = shan_entropy(c_Y)
H_XY = shan_entropy(c_XY)
MI = H_X + H_Y - H_XY
return MI
def shan_entropy(c):
c_normalized = c / float(np.sum(c))
c_normalized = c_normalized[np.nonzero(c_normalized)]
H = -sum(c_normalized* np.log2(c_normalized))
return H
A = np.array([[ 2.0, 140.0, 128.23, -150.5, -5.4 ],
[ 2.4, 153.11, 130.34, -130.1, -9.5 ],
[ 1.2, 156.9, 120.11, -110.45,-1.12 ]])
bins = 5 # ?
n = A.shape[1]
matMI = np.zeros((n, n))
for ix in np.arange(n):
for jx in np.arange(ix+1,n):
matMI[ix,jx] = calc_MI(A[:,ix], A[:,jx], bins)
ネストされたループを使用した私の作業バージョンは妥当な速度で実行されますが、 (ペアごとの相互情報を計算するために) のすべての列にfor
適用するより最適な方法があるかどうかを知りたいですか?calc_MI
A
私も知りたいです:
関数をマップして列 (または行) を操作する効率的な方法があるかどうか (
np.arrays
デコレータnp.vectorize
のように見える のように)?この特定の計算に最適な実装が他にあるかどうか (相互情報)?