我想使用索引切片沿其2个轴切片多维numpy数组(> 2维)。每个原始尺寸在哪里结束的规则是什么?
为说明我的问题,让我提供一个示例。假设我们有一个4D阵列:
import numpy as np
a = np.arange(2*3*4*5).reshape(2,3,4,5)
我将使用numpy.where创建一个索引元组,以沿轴1和3进行切片。
mask = np.where(np.random.rand(3,5) > 0.5)
这将从我的数组a
中选择随机切片。假设它返回长度为7的元组。
为了保留剩余的尺寸,我将使用slice(None)
对象:
b = a[(slice(None), mask[0], slice(None), mask[1])]
这改变了形状:
>>> a.shape
(2, 3, 4, 5)
>>> b.shape
(7, 2, 4)
未触摸的轴(即使用slice(None)
对象进行了切片)似乎已保留,而切片的轴被破坏,结果轴移到了前面。
但是,并非总是如此。当我将遮罩应用于轴1和2时:
mask2 = np.where(np.random.rand(3,4) > 0.5)
c = a[(slice(None), mask[0], mask[1], slice(None))]
我观察到以下情况(numpy.where又返回了长度为7的元组):
>>> c.shape
(2, 7, 5)
这次被切片破坏的轴所产生的轴没有移到前面。
我的猜测是,这与切片轴是否相邻有关,但是我想知道从什么规则中会出现这种行为。
答案 0 :(得分:3)
如果将where
蒙版应用于2d数组,则条件条件为true时,将生成1d (7,)
形状数组。您可以说这是在“消灭”一对轴。
在第二种情况下,可以将7
放在2
和5
之间。
但是在第一个中它是模棱两可的,因为中间是切片(非邻接)-后退规则是将其放在第一位,然后对切片排序。换句话说,它没有选择(2,7,4)和(2,4,7)顺序,而是选择(7,2,4)。
在这种情况下,歧义很明显,默认情况下是合理的。用标量索引消除一个或多个维度会更加复杂。