numpy 二维数组索引

y0u0uwnf  于 2023-03-08  发布在  其他
关注(0)|答案(2)|浏览(185)

我如何对一些用作索引的数组进行索引?我有如下的二维数组:

array([
   [2, 0],
   [3, 0],
   [3, 1],
   [5, 0],
   [5, 1],
   [5, 2]
])

我想使用这个数组作为索引,并将值10放入一个新的空矩阵的相应索引中,输出应该如下所示:

array([
   [ 0,  0,  0],
   [ 0,  0,  0],
   [10,  0,  0],
   [10, 10,  0],
   [ 0,  0,  0],
   [10, 10, 10]
])

到目前为止我试过这个-

from numpy import*
a = array([[2,0],[3,0],[3,1],[5,0],[5,1],[5,2]])
b = zeros((6,3), dtype ='int32')
b[a] = 10

但这给了我错误的输出。

cbwuti44

cbwuti441#

In [1]: import numpy as np
In [2]: a = np.array([[2,0],[3,0],[3,1],[5,0],[5,1],[5,2]])
In [3]: b = np.zeros((6,3), dtype='int32')

In [4]: b[a[:,0], a[:,1]] = 10

In [5]: b
Out[5]: 
array([[ 0,  0,  0],
       [ 0,  0,  0],
       [10,  0,  0],
       [10, 10,  0],
       [ 0,  0,  0],
       [10, 10, 10]])

工作原理:

如果你在赋值语句中用两个numpy数组来索引b

b[x, y] = z

然后将NumPy视为同时在x的每个元素、y的每个元素和z的每个元素上移动(我们称之为xvalyvalzval),并将值zval赋给B[xval,yval]。当z是常数时,“在z上移动每次只返回相同的值。
这就是我们想要的,xa的第一列,ya的第二列,因此,选择x = a[:, 0]y = a[:, 1]

b[a[:,0], a[:,1]] = 10

为什么b[a] = 10不起作用

当你写b[a]时,把NumPy看作是通过移动a的每个元素(我们称每个元素为idx)来创建一个新数组,并把b[idx]的值放在aidx的位置。
idxa中的值。因此它是int32。b的形状为(6,3),因此b[idx]b的形状为(3,)的行。例如,当idx

In [37]: a[1,1]
Out[37]: 0

b[a[1,1]]

In [38]: b[a[1,1]]
Out[38]: array([0, 0, 0])

所以

In [33]: b[a].shape
Out[33]: (6, 2, 3)

我们再重复一遍:NumPy正在创建一个新数组,方法是移动a的每个元素,并将b[idx]的值放入新数组中aidx的位置。当idx移动到a上时,将生成一个形状为但由于b[idx]本身的形状为(3,),因此在形状为(6,2)的数组中的每个位置都放置了形状为(3,)的值,结果是形状为(6,2,3)的数组。
现在,当你做一个

b[a] = 10

形状的临时阵列(6,2,3),然后执行赋值。由于10是常数,因此此赋值将值10放置在(6,2,3)形状的数组。然后临时数组中的值被重新分配回b。请参阅参考文档。因此(6,2,3)型数组被复制回(6,3)型b数组。值会相互覆盖。但主要的一点是,你没有得到你想要的赋值。

gijlo24d

gijlo24d2#

您也可以转置索引数组a,将结果转换为元组,然后为数组b建立索引并赋值。将索引数组转换为元组可确保多维索引按预期工作。

a = np.array([[2, 0], [3, 0], [3, 1], [5, 0], [5, 1], [5, 2]])
b = np.zeros((6,3), dtype ='int32')

b[tuple(a.T)] = 10
# or 
b[(*a.T,)] = 10
# or 
b[(*a.T.tolist(),)] = 10

所有这些都产生预期输出

array([[ 0,  0,  0],
       [ 0,  0,  0],
       [10,  0,  0],
       [10, 10,  0],
       [ 0,  0,  0],
       [10, 10, 10]])

相关问题