我有一个类似ids = ([0,0,0,1,1,2,2,2,2,4,5,5,5])
的numpy数组和一些长度相同的其他numpy数组(比如a
和b
)。我想使用这些数组的切片执行一些独立的操作,切片定义为共享相同(连续)id组的索引。即我想定义一组像
slice_0 = 0:3
slice_1 = 3:5
slice_2 = 5:9
...
这样我就可以并行地为每个n调用一个函数f(a[slice_n],b[slice_n])
。如何在numpy中构建切片?如果它有帮助,在R中我会用tapply
。
答案 0 :(得分:1)
我不确定我理解你的问题,也许你打算
slice_0 = 0:3
slice_1 = 3:5
slice_2 = 5:9
slice_3 = 9:10
slice_4 = 10:13
如果是这种情况,您可以使用NumPy unique:
_, idx, count = numpy.unique(ids, return_index=True, return_counts=True)
切片的下限为idx
,上限为idx + count
。
答案 1 :(得分:1)
获得分割点:
spl=np.r_[0, np.where(np.nonzero(np.diff(ids)))[0] + 1, ids.size]
然后是切片列表
slices=[slice(i,j) for i,j in zip(spl[:-1].flat, spl[1:].flat)]
或拆分其他数组
a_spl=np.split(a,spl[1:-1])
编辑:由于idx
已按顺序排序,您可以执行上面的unique
或执行布尔切片(如果您有内存)
slices = list(np.unique(ids)[:,None] == ids[None,:])
答案 2 :(得分:0)
一种方法:
In [12]: arrays=vstack((a,b))
In [13]: arrays
Out[13]:
array([[4, 1, 4, 2, 5, 7, 1, 5, 9],
[8, 1, 1, 1, 9, 3, 0, 3, 1]])
In [14]: subarrays=np.split(arrays,[3,5],axis=1)
In [15]: subarrays
Out[15]:
[array([[4, 1, 4],
[8, 1, 1]]),
array([[2, 5],
[1, 9]]),
array([[7, 1, 5, 9],
[3, 0, 3, 1]])]
In [16]: [multiply(a,b) for (a,b) in subarrays]
Out[16]: [array([32, 1, 4]), array([ 2, 45]), array([21, 0, 15, 9])]
答案 3 :(得分:0)
如果你想沿着轴将数组切成块,最简单的方法是np.split
:
>>> a = np.arange(10)
>>> split_points = (2,5,7)
>>> np.split(a, split_points)
[array([0, 1]), array([2, 3, 4]), array([5, 6]), array([7, 8, 9])]
如果您想要分割,则可以np.arange
使用split_points
。
要使用split_points = np.where(np.diff(ids))[0] + 1
如果您的id数组已排序,并且您还没有重复的ID,那么split_points = np.searchsorted(ids, ids_wor)[1:]
可能会更快。