Python 如何有效地计算嵌套循环中上三角形的logsumexp?

Python 如何有效地计算嵌套循环中上三角形的logsumexp?,python,numpy,matrix,vectorization,linear-algebra,Python,Numpy,Matrix,Vectorization,Linear Algebra,我有一个嵌套的for循环,它迭代权重矩阵的行,并将logsumexp应用于这些权重行的外部加法矩阵的上三角部分。它非常慢,所以我试图找出如何通过矢量化或去掉循环来代替矩阵运算来加快速度 ''' Wm: weights matrix, nxk W: updated weights matrix, nxn triu_inds: upper triangular indices of Wxy outer matrix ''' for x in range(n-1): wx = Wm[x, :

我有一个嵌套的for循环,它迭代权重矩阵的行,并将logsumexp应用于这些权重行的外部加法矩阵的上三角部分。它非常慢,所以我试图找出如何通过矢量化或去掉循环来代替矩阵运算来加快速度

'''
Wm: weights matrix, nxk
W: updated weights matrix, nxn
triu_inds: upper triangular indices of Wxy outer matrix
'''

for x in range(n-1):
    wx = Wm[x, :]
    for y in range(x+1, n):
        wy = Wm[y, :]
        Wxy = np.add.outer(wx, wy)
        Wxy = Wxy[triu_inds]
        W[x, y] = logsumexp(Wxy)
logsumexp:计算输入数组的指数和的日志

a: [1, 2, 3]
logsumexp(a) = log( exp(1) + exp(2) + exp(3) )
输入数据Wm是nxk维的权重矩阵。K表示患者传感器位置,n表示所有此类可能的传感器位置。Wm中的值基本上是患者传感器与已知传感器的距离

例如:

Wm  = [1   2   3]
      [4   5   6]
      [7   8   9]
      [10 11  12]

wx  = [1   2   3]
wy  = [4   5   6]

Wxy = [5   6   7]
      [6   7   8]
      [7   8   9]

triu_indices = ([0, 0, 1], [1, 2, 2])
Wxy[triu_inds] = [6, 7, 8]
logsumexp(Wxy[triu_inds]) = log(exp(6) + exp(7) + exp(8))

您可以对完整矩阵
Wm
执行外积,然后交换与操作数1中的列和操作数2中的行相对应的轴,以便将三角形索引应用于列。生成的矩阵将填充所有行的组合,因此需要选择上部三角形部分

W = logsumexp(
    np.add.outer(Wm, Wm).swapaxes(1, 2)[(slice(None),)*2 + triu_inds],
    axis=-1  # Perform summation over last axis.
)
W = np.triu(W, k=1)

您可以对完整矩阵
Wm
执行外积,然后交换与操作数1中的列和操作数2中的行相对应的轴,以便将三角形索引应用于列。生成的矩阵将填充所有行的组合,因此需要选择上部三角形部分

W = logsumexp(
    np.add.outer(Wm, Wm).swapaxes(1, 2)[(slice(None),)*2 + triu_inds],
    axis=-1  # Perform summation over last axis.
)
W = np.triu(W, k=1)

您能否给出数据和预期输出的示例,以及
logsumexp
的定义?
W
有什么形状?在您的示例中,
y
的范围取决于
x
,因此
W
的下三角仍然未填充?是吗?是的,只有W的上三角部分是对称的。如果您可以在不使用python循环的情况下填充所有的
W
,则速度会更快,即使存在一些重复值。您能否给出数据和预期输出的示例,以及
logsumexp
的定义,
W
有什么形状?在您的示例中,
y
的范围取决于
x
,因此
W
的下三角仍然未填充?是吗?是的,只有W的上三角部分是对称的。如果您可以在不使用python循环的情况下填充所有的
W
,则速度会更快,即使存在一些重复值。