# 3.3 NumPy数组广播机制

## 3.3 NumPy数组广播机制

Numpy数组广播机制用于处理不同形状数组之间的运算。其机理是：运算前先使两个数组的维数相同，且各维度的长度相同；形状对齐后再按对应位置做逐元素运算。3.1.3节指出数组与数组运算要求两数组形状相同，广播正是把形状不同的数组先扩充到形状相同。常用写法是：先执行`import numpy as np`，再用`np.arange()`与`reshape()`构造数组，用`ndim`、`shape`查看维数和各维长度，最后用加法、乘法等运算符触发广播。广播在运算时自动发生。

广播规则有两条。规则一：如果两个数组的维数不同，在维数较小的数组前面补1，直到两个数组的维数相同。规则二：从左到右逐维检查两个数组的长度；如果长度不同且有一个长度为1，则扩充长度为1的维度，直到两个数组形状相等；如果长度不同且都不为1，则不能扩充。

【例3-1】形状为(3,2)的数组`a`与形状为(2,)的数组`b`做`a+b`。先按规则一把`b`的形状扩充为(1,2)，再按规则二把长度为1的维度扩充为3，`b`变为(3,2)，结果为`array([[1, 3], [3, 5], [5, 7]])`。示例代码如下。

```python
import numpy as np
a = np.arange(6).reshape(3, 2)
b = np.arange(1, 3)
print(a + b)
```

【例3-2】形状(2,3)与(2,1)维数已经相同无须补1，第一维长度都是2，只需把`b`的第二维由1扩充为3，结果为`array([[1, 2, 3], [5, 6, 7]])`。

易错点：补1必须加在维数较小数组的前面，不能补在后面；规则二要求“有一个长度为1才能扩充”，两维长度不同且都不为1时不能硬凑。【例3-3】形状(2,3)与(3,1)虽然都是二维数组，但第一维长度2与3都不为1，不满足广播规则，不能运算。不要因为两边都出现数字3就误判可以广播。广播只作用于本次运算，并不改写原数组对象本身。

## 关键要点
- 广播机制用于处理不同形状数组之间的运算，机理是使维数相同且各维长度相同。
- 规则一：维数不同时在维数较小的数组前面补1。
- 规则二：从左到右逐维检查，长度不同且有一个为1才可扩充；都不为1则不能扩充。
- 形状对齐后按对应位置逐元素运算；`arange`、`reshape`、`shape`与加减乘等运算符即可完成演示。
- 补1只能加在前面；形状(2,3)与(3,1)是典型的不能广播情形。
- 广播不改写原数组对象。
