numpy 索引切片迭代
对于一维数组,和Python列表一样进行索引、切片和迭代。
>>> a = np.arange(10)**3
>>> a
array([ 0, 1, 8, 27, 64, 125, 216, 343, 512, 729])
>>> a[2]
8
>>> a[2:5]
array([ 8, 27, 64])
>>> a[:6:2] = -1000 # 首先按步长区间切片,然后将每个元素设置为-1000
>>> a
array([-1000, 1, -1000, 27, -1000, 125, 216, 343, 512, 729])
>>> a[ : :-1] # 反转a
array([ 729, 512, 343, 216, 125, -1000, 27, -1000, 1, -1000])
>>> for i in a:
... print(i)
-1000
1
-1000
27
-1000
125
216
343
512
729
numpy的切片操作,默认是修改原数组的,而不是原生Python那样,以复制为主。
对于多维数组,每个轴都有一个索引index,并以逗号分隔:
>>> b=np.array([[ 0, 1, 2, 3],
[10, 11, 12, 13],
[20, 21, 22, 23],
[30, 31, 32, 33],
[40, 41, 42, 43]])
>>> b[2,3] # 第3行第4列的元素,注意索引从0开始计数
23
>>> b[2][3]
23
>>> b[0:5, 1] # 第二列中的每一行,注意区间的左闭合右开的特性
array([ 1, 11, 21, 31, 41])
>>> b[ : ,1] # 相当于上面的例子
array([ 1, 11, 21, 31, 41])
>>> b[1:3, : ] # 每一列的,第二行和第三行的元素
array([[10, 11, 12, 13],
[20, 21, 22, 23]])
>>> b[-1] #当给与的参数少于轴数时,其它的轴被认为是全选,比如这里获得最后一行,等同于b[-1,:]
array([40, 41, 42, 43])
在上面的最后例子中,省略了列的索引。有时候,它们会被写作这样的格式x[i,...]
。三个连续的圆点,代表其它未给出的所有轴的索引。例如假设有数组x,它有5个轴,那么:
x[1,2,...]
相当于x[1,2,:,:,:]
x[...,3]
相当于x[:,:,:,:,3]
x[4,...,5,:]
相当于x[4,:,:,5,:]
参考下面的例子:
>>> c = np.array( [[[ 0, 1, 2],
... [ 10, 12, 13]],
... [[100,101,102],
... [110,112,113]]])
>>> c.shape
(2, 2, 3)
>>> c[1,...] # 等同于c[1,:,:] or c[1]
array([[100, 101, 102],
[110, 112, 113]])
>>> c[...,2] # 等同于c[:,:,2]
array([[ 2, 13],
[102, 113]])
这是偷懒的做法,不建议使用,省不了多少事,但带来的理解困难却很多。
对于多维数组的迭代其实就是对它的第一轴进行迭代,从下例子中可以看出,每个被打印的对象都是原来的一行:
>>> for row in b:
... print(row)
...
[0 1 2 3]
[10 11 12 13]
[20 21 22 23]
[30 31 32 33]
[40 41 42 43]
如果想对多维数组进行类似Python列表的那样迭代,可以使用数组的flat属性,如下例所示:
>>> for element in b.flat:
... print(element)
...
0
1
2
3
10
11
12
...