【问题标题】:Update numpy at each index based on the previous index根据前一个索引在每个索引处更新 numpy
【发布时间】:2018-11-23 20:35:48
【问题描述】:

是否有一种矢量化的方法可以根据之前的索引更新 numpy 数组中的每个任意索引?例如,在伪代码中,如果我有矩阵

1 2 3
3 1 4
1 3 2

对于每个索引 (i, j),我想做:

m[i,j] += max(m[i, j-1], m[i-1, j])

现在我知道我可以迭代地执行此操作,但我想知道是否有一种矢量化方式来执行此操作,因为它比一遍又一遍地从 numpy 数据空间中取出更有效。

另外,我知道这是一个栅栏张贴问题,因为 m[0, 0] 没有前一个元素。这可以通过在矩阵中添加额外的 0 行和列来轻松解决。

【问题讨论】:

  • 考虑使用numba

标签: python numpy


【解决方案1】:

这是一种矢量化它的方法:

arr = np.array([[1, 2, 3],[3, 1, 4],[1, 3, 2]])

arr_A = np.roll(arr, 1, axis=0)
arr_B = np.roll(arr, 1, axis=1)

max_val = np.maximum(arr_A, arr_B)

output = arr + max_val
>>> [[4 5 5]
     [7 4 7]
     [4 4 6]]

请注意,这对您上面的代码给出了不同的答案,因为您编写代码的方式意味着值在每次循环后都会更新。如果你想这样做,那么你必须使用for 循环。

>>> [[ 4  6  9] # Output after updating the matrix in each loop.
     [ 7  8 13]
     [ 8 11 15]]

如果您正在寻找一种类似的算法而不是试图恢复这个精确的输出,那么np.roll() 应该可以加快速度。

【讨论】:

    【解决方案2】:

    您可以使用numpy.roll 创建矩阵的移位版本:

    m += np.maximum(np.roll(m, 1, axis=0), np.roll(m, 1, axis=1))
    

    不过,这会创建两个新副本。零填充是必需的,因为 roll 重新引入了“滚动”超出边界的元素:

    p = np.pad(m, [(1, 1), (1, 1)], 'constant')
    m += np.maximum(np.roll(p, 1, axis=0), np.roll(p, 1, axis=1))[1:-1, 1:-1]
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-10-25
      • 1970-01-01
      • 2015-07-01
      • 1970-01-01
      • 1970-01-01
      • 2017-08-17
      • 1970-01-01
      • 2018-04-10
      相关资源
      最近更新 更多