首页 > 解决方案 > 获取不同长度的索引以对多维 numpy 数组进行切片

问题描述

鉴于这些数组,

  R = np.array([[ 5.,  3.,  2.,  7.,  3.,  6.,  8.,  9., 10., 55.],
                  [ 5.,  4.,  2.,  7.,  3.,  6.,  8., 10., 10., 55.]])
  F = np.array([[ 0.2 ,  0.4 ,  0.1 ,  0.3 ,  0.25,  0.25,  0.2 ,  0.1 ,  0.1 , 0.1 ],
                  [ 0.3 , -0.4 ,  0.1 ,  0.3 ,  0.25,  0.25,  0.4 , -0.4 ,  0.1 , 0.1 ]])
  K = nparray([[2],
                 [1]])

我想对 的每一行进行排序F,然后找到sortedK[0]的第一行的第一个索引和第二行的第一个索引。然后使用这些索引,我想将 1 添加到.K[1]FR

这是我的尝试,我能够获得索引:

indices = np.argsort(F)[np.tile(np.arange(F.shape[1]),(F.shape[0],1)) < K]
# indices =  np.array([7, 8, 7], dtype=int64)

但我不确定如何在不使用 for 循环的情况下对以下操作进行矢量化。

Rnew = R.copy()

Rnew[0,7] =R[0,7]+1

Rnew[0,8] =R[0,8]+1

Rnew[1,7] =R[1,7]+1

Rnew = np.array([[ 5.,  3.,  2.,  7.,  3.,  6.,  8., 10., 11., 55.],
                 [ 5.,  4.,  2.,  7.,  3.,  6.,  8., 11., 10., 55.]])

标签: pythonnumpynumpy-slicing

解决方案


我认为这应该有效:

m = np.arange(F.shape[1]) < K
Rnew = R.copy()
Rnew[np.nonzero(m)[0], np.argsort(F)[m]] += 1

由于第一行使用广播,np.tile()因此不需要。

请注意,结果可能存在歧义:由于 的每一行F具有重复多次的值(例如,第一行中的 0.1 和第二行中的 -0.4)np.argsort()可能会给出 的元素的不同顺序F,具体取决于这些相等值的方式得到排序。这可能会改变矩阵的哪些条目R将增加。例如,代码可以增加条目和,而不是递增R[0, 7]、和。要获得明确的结果,您可以指定必须使用稳定的排序算法,该算法将保留具有相等值的元素的相对顺序:R[0, 8]R[1, 7]R[0, 2]R[0, 9]R[1, 1]np.argsort()

m = np.arange(F.shape[1]) < K
Rnew = R.copy()
Rnew[np.nonzero(m)[0], np.argsort(F, kind="stable")[m]] += 1

在此特定示例中,这将增加条目R[0, 2]和。您需要确定这是否是满足您需求的结果。R[0, 7]R[1, 1]


推荐阅读