30分钟
多维数组的索引
- 多维数组使用元组作为数组的下标,如
a[1,2]
,当然你也可以添加圆括号为a[(1,2)]
。- 元组中每个元素和数组的每个轴对应。下标元组的第 0 个元素与数组的第 0 轴对应,如第 1 个元素与数组的第 1 轴对应...
- 多维数组的下标必须是一个长度和数组的维度
ndim
相等的元组。- 如果下标元组的长度大于数组的维度
ndim
,则报错 - 如果下标元组的长度小于数组的维度
ndim
,则在元组的后面补:
,使得下标元组的长度等于数组维度ndim
。 - 如果下标对象不是元组,则
Numpy
会首先将其转换为元组。 - 下面的讨论都是基于下标元组的长度等于数组维度
ndim
的条件。
- 如果下标元组的长度大于数组的维度
- 单独生成切片时,需要使用
slice(begin,end,step)
来创建。其参数分别为:开始值,结束值,间隔步长。如果某些参数需要省略,则使用None
。因此,a[2:,2]
等价于a[slice(2,None,None),2]
- 使用
python
内置的slice()
创建下标比较麻烦(首先构造切片,再构造下标元组),numpy
提供了一个numpy.s_
对象来帮助我们创建数组下标。s_
对象实际上是IndexExpression
类的一个对象
- 使用
4. 多维数组的下标元组的元素可能为下列类型之一:整数、切片、整数数组、布尔数组。如果不是这些类型,如列表或者元组,则将其转换成整数数组。
- 多维数组的下标全部是整数或者切片:索引得到的是元素数组的一个视图。
- 多维数组的下标全部是整数数组:假设多维数组为X。假设这些下标整数数组依次为A1,A2,⋯,An 。这n 个数组必须满足广播条件。假设它们进行广播之后的维度为 M ,形状为(d_0,d_1,⋯,d_{M−1}) 即:广播之后有 M个轴:第 0 轴长度为 d_0 ,...,第 M−1轴长度为d_{M-1} 。假设 A1,A2,⋯,An经过广播之后分别为数组 A′1,A′2,⋯,A′n 则:索引的结果也是一个数组 R ,结果数组R的维度为M ,形状为(d0,d1,⋯,dM−1) 。其中
结果数组的下标并不来源于 ,而是来源于下标数组的广播之后的数组。相反,如果多维数组的下标为整数或者切片,则结果数组的下标来源于
5. 当下标使用整数或者切片时,所取得的数据在数据存储区域中是等间隔分布的。因为只需要修改数组的ndim/shape/strides
等属性以及指向数据存储区域的data
指针就能够实现整数和切片下标的索引。所以新数组和原始数组能够共享数据存储区域。
当使用整数数组(整数元组,整数列表页转换成整数数组),布尔数组时,不能保证所取得的数据在数据存储区中是等间隔的,因此无法和原始数组共享数据,只能对数据进行复制。
6. 索引的下标元组中:
- 如果下标元组都是切片,则索引结果的数组与原始数组的维度相同(轴的数量相等)
- 每多一个整数下标,则索引结果的数组就少一个维度(少一个轴)
- 如果所有的下标都是整数,则索引结果的维度为 0
如果下标元组中存在数组,则还需要考虑该下标数组广播后的维度
7. 通过索引获取的数组元素的类型为数组的dtype
类型 。如果你想获取标准python
类型,可以使用数组的item()
方法。
学员评价