独立移动 numpy 数组的行 [英] Shift rows of a numpy array independently
问题描述
这是在此处提出的问题的扩展(引述如下)
This is an extension of the question posed here (quoted below)
我有一个矩阵(准确地说是二维 numpy ndarray):
I have a matrix (2d numpy ndarray, to be precise):
A = np.array([[4, 0, 0],
[1, 2, 3],
[0, 0, 5]])
我想根据roll独立滚动A的每一行另一个数组中的值:
And I want to roll each row of A independently, according to roll values in another array:
r = np.array([2, 0, -1])
也就是说,我想这样做:
That is, I want to do this:
print np.array([np.roll(row, x) for row,x in zip(A, r)])
[[0 0 4]
[1 2 3]
[0 5 0]]
有没有办法有效地做到这一点?也许使用花哨的索引技巧?
Is there a way to do this efficiently? Perhaps using fancy indexing tricks?
接受的解决方案是:
rows, column_indices = np.ogrid[:A.shape[0], :A.shape[1]]
# Use always a negative shift, so that column_indices are valid.
# (could also use module operation)
r[r < 0] += A.shape[1]
column_indices = column_indices - r[:,np.newaxis]
result = A[rows, column_indices]
我基本上想做同样的事情,除非当索引滚动超过"行尾时,我希望行的另一侧用 NaN 填充,而不是将值移动到以周期性的方式行的前面".
I would basically like to do the same thing, except when an index gets rolled "past" the end of the row, I would like the other side of the row to be padded with a NaN, rather than the value move to the "front" of the row in a periodic fashion.
也许以某种方式使用 np.pad
?但我不知道如何让它以不同的数量填充不同的行.
Maybe using np.pad
somehow? But I can't figure out how to get that to pad different rows by different amounts.
推荐答案
Inspired by 独立滚动矩阵行的解决方案,这是一个基于 np.lib.stride_tricks 的矢量化方法.as_strided
-
Inspired by Roll rows of a matrix independently's solution, here's a vectorized one based on np.lib.stride_tricks.as_strided
-
from skimage.util.shape import view_as_windows as viewW
def strided_indexing_roll(a, r):
# Concatenate with sliced to cover all rolls
p = np.full((a.shape[0],a.shape[1]-1),np.nan)
a_ext = np.concatenate((p,a,p),axis=1)
# Get sliding windows; use advanced-indexing to select appropriate ones
n = a.shape[1]
return viewW(a_ext,(1,n))[np.arange(len(r)), -r + (n-1),0]
样品运行 -
In [76]: a
Out[76]:
array([[4, 0, 0],
[1, 2, 3],
[0, 0, 5]])
In [77]: r
Out[77]: array([ 2, 0, -1])
In [78]: strided_indexing_roll(a, r)
Out[78]:
array([[nan, nan, 4.],
[ 1., 2., 3.],
[ 0., 5., nan]])
这篇关于独立移动 numpy 数组的行的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!