当我们有M
形状(a, b, c)
和我们用来索引最后一个数组的索引数组v
时,为什么M[i, :, v]
会产生一个形状数组(d, b)
{d
v
中的真值数量是多少?如下图所示:
In [409]: M = zeros((100, 20, 40))
In [410]: val = ones(shape=(40,), dtype="bool")
In [411]: M[0, :, :].shape
Out[411]: (20, 40) # As expected
In [412]: M[0, :, val].shape
Out[412]: (40, 20) # Huh? Why (40, 20), not (20, 40)?
In [413]: M[:, :, val].shape
Out[413]: (100, 20, 40) # s expected again
为什么M[0, :, val]
形成(40, 20)
而不是(20, 40)
?
答案 0 :(得分:3)
根据文档的boolean indexing
部分
http://docs.scipy.org/doc/numpy/reference/arrays.indexing.html#boolean-array-indexing
使用obj.nonzero()类比可以最好地理解组合多个布尔索引数组或布尔与整数索引数组。
ind = np.nonzero(val)[0]
# array([ 0, 1, 2, ...., 39], dtype=int32)
M[0, :, ind].shape # (40,20)
现在我们转到有关组合高级和基本索引的部分 http://docs.scipy.org/doc/numpy/reference/arrays.indexing.html#combining-advanced-and-basic-indexing
这是一种形式:x[arr1, :, arr2]
在第一种情况下,高级索引操作产生的维度首先出现在结果数组中,然后是子空间维度。
因此0
和ind
部分会产生(40,)
个选择,而中间的:
产生(20,)
。通过将:
部分放在最后,结果维度为(40,20)
。基本上它是这样做的,因为这种索引样式存在歧义,因此它始终选择将切片部分放在最后。
选择这些值并保持所需形状(或多或少)的方法是使用np.ix_
生成索引元组。
M[np.ix_([0],np.arange(20),ind)].shape # (1, 20, 40)
您可以使用np.squeeze
删除最初的1
尺寸。
“纯索引数组索引”部分的末尾说明了ix_
的这种用法
http://docs.scipy.org/doc/numpy/reference/arrays.indexing.html#purely-integer-array-indexing