一、数组操作
数组的操作主要可以分为连接和切分两种。Numpy库使用了栈的概念完成上述操作。
(1)数组连接
在数组连接方面,Numpy库提供了函数vstack() 和函数 hstack() 分别用于执行垂直入栈操作和水平入栈操作。
import numpy as np
a = np.eye(3)
b = np.eye(3)
print('垂直插入:\n', np.vstack((a, b)))
print('水平插入:\n', np.hstack((a, b)))
输出结果如下:
垂直插入:
[[1. 0. 0.]
[0. 1. 0.]
[0. 0. 1.]
[1. 0. 0.]
[0. 1. 0.]
[0. 0. 1.]]
水平插入:
[[1. 0. 0. 1. 0. 0.]
[0. 1. 0. 0. 1. 0.]
[0. 0. 1. 0. 0. 1.]]
需要注意的是,传入参数必须为一个元组类型。
(2)数组切分
在数组连接方面,Numpy库提供了函数vsplit() 和函数 hsplit() 分别用于将数组的高度或长度进行等分分割。
import numpy as np
a = np.ones((4, 4))
print('*'*10, '长度等分', '*'*10)
[b, c] = np.hsplit(a, 2)
print('b数组:\n', b, '\nc数组:\n', c)
print('*'*10, '高度等分', '*'*10)
[b, c] = np.vsplit(a, 2)
print('b数组:\n', b, '\nc数组:\n', c)
输出结果如下:
b数组:
[[1. 1.]
[1. 1.]
[1. 1.]
[1. 1.]]
c数组:
[[1. 1.]
[1. 1.]
[1. 1.]
[1. 1.]]
********** 高度等分 **********
b数组:
[[1. 1. 1. 1.]
[1. 1. 1. 1.]]
c数组:
[[1. 1. 1. 1.]
[1. 1. 1. 1.]]
此外,Numpy库还提供了用于不对称切分的函数split(),其内包含三个参数:
- 传入的第一个参数ary表示需要被切分的数组
- 传入的第二个参数indices_or_sections表示需要切分的位置或方法
– 若传入为一个数字,则代表切分后,每份数组的长度
– 若传入的为一个列表,则代表原数组中需要被切分的元素的索引位置
– 传入列表的范围为左闭右开 - 传入的第三个参数axis表示按照行或则列的方式进行切分
– 若值为0,则按行切分
– 若值为1,则按列切分
import numpy as np
a = np.arange(1, 10)
print('原数组:', a)
print('等分切割:', np.split(a, 3, axis=0))
print('指定切割:', np.split(a, [1,5,7], axis=0))
输出结果如下:
原数组: [1 2 3 4 5 6 7 8 9]
等分切割: [array([1, 2, 3]), array([4, 5, 6]), array([7, 8, 9])]
指定切割: [array([1]), array([2, 3, 4, 5]), array([6, 7]), array([8, 9])]
二、广播机制
广播机制实现了对两个或以上的形状不同的数组进行运算或用函数处理。广播机制满足如下原则:
- 兼容性原则:所处理的两个(或以上)的数组每一维等长,或则其中一个数组为一维数组。
- 所有所处理的数组都向其中形状最长的数组看齐,形状中不足的部分都通过在前面加 1 补齐。
- 输出数组的形状是所处理的数组形状的各个维度上的最大值。
- 当所处理的数组的某个维度的长度为 1 时,沿着此维度运算时都用此维度上的第一组值。
若所处理的两个数组列数相同且其中一个为一维数组,则可以通过如下方式进行处理:
import numpy as np
a = np.arange(0, 6).reshape(2, 3)
b = np.arange(0, 3)
print(a+b)
输出结果如下:
[[0 2 4]
[3 5 7]]
若所处理的两个数组维度相同且其中一个数组在列数上仅为一,则可以通过如下方式进行处理:
import numpy as np
a = np.arange(0, 6).reshape(2, 3)
b = np.arange(0, 2).reshape(2, 1)
print(a+b)
输出结果如下:
[[0 1 2]
[4 5 6]]
若所处理的两个数组中有一个为单元素,则可以通过如下方式进行处理:
import numpy as np
a = np.arange(0, 6).reshape(2, 3)
print(a+2)
输出结果如下:
[[2 3 4]
[5 6 7]]
若所处理的两个二维数组在不同维度上为一维数组,则可以通过如下方式进行处理:
import numpy as np
a = np.array([
[0],
[3]
])
b = np.arange(0, 3)
print(a+b)
输出结果如下:
[[0 1 2]
[3 4 5]]
三、视图和副本
视图表示为对数据的一个引用而不产生拷贝,通过该引用可以方便于访问、操作原有数据。副本则是对数据的完整拷贝。如果对视图进行修改,将直接修改到原数据上;如果对副本进行修改,则不会影响到原数据。
视图一般发生在:
- 对数组进行切片操作时返回的数组为原数组的视图
- 通过调用Numpy库的内置函数view() 能够产生视图
副本一般发生在:
- Python 序列的切片操作,调用deepCopy()函数。
- 通过调用Numpy库的内置函数 copy() 能够产生副本