神经网络怎样把直线组合成曲线:隐藏层与深度的直觉 · znzryb
# 神经网络怎样把直线组合成曲线:隐藏层与深度的直觉
主要参考:[Luis Serrano 的 A friendly introduction to Deep Learning and Neural Networks](https://www.youtube.com/watch?v=BR9h47Jtqyw)。本文是结合观看截图与手写批注整理的中文学习笔记,截图来自该视频及观看时的批注,原视频与画面版权归原作者所有。
本篇按截图时间顺序放第 21—35 张原图。前两篇解释了怎样训练一条直线,以及一个神经元如何输出概率;现在面对一条直线分不开的数据,看看多个神经元如何一起工作。
## 一条直线不够,就让多个单元提供不同的判断

*截图 21|非线性分类目标:蓝点分布需要一条弯曲边界*
蓝点被红点从几侧包围。无论怎么挪动一条直线,都会顾此失彼。我们需要更灵活的函数,但可以先复用已经理解的逻辑回归单元。

*截图 22|两个分类单元分别切分平面,提供两种不同的位置特征*
一个单元判断点更像在某条线的上方,另一个判断点更像在另一条线的右方。同一个点进入两个单元,会得到两个不同的输出。这不是复制数据后各自完成任务,而是在为最后的判断提取两种特征。

*截图 23|将两个单元的连续输出交给下一层,得到新的分类区域*
下一层接收到的是两个连续数值,而不仅是两个“是或否”。它可以综合这些数值,决定哪些位置最终偏蓝。对原始坐标来说,这个组合已经可能产生弯曲边界。

*截图 24|完整目标总览:组合简单区域,得到更灵活的最终区域*
这里的加号是一种教学记号,表示**组合两个函数的输出**。它不是把两张图片叠加,也不能直接理解成集合求并或求交。具体区域长什么样,取决于权重、偏置、激活函数和分类阈值。
## 两个概率相加,还差什么

*截图 25|示例点在两个单元中输出 0.7 与 0.8,合计分数为 1.5*
同一个点得到 $0.7$ 与 $0.8$,相加是 $1.5$;它可以当下一层的分数,但不是概率。再经过 Sigmoid,得到约 $0.8176$,与截图里的 $0.82$ 一致。
这一步说明了“前一层的输出也能作为后一层的输入”。不过,若直接对两个 0—1 输出求和再用 Sigmoid,结果始终大于 $0.5$,采用 $0.5$ 阈值时就会把所有点判成蓝色。**所以这只是计算过程的过渡示例,不能据此认为曲线分类已经完成。**接下来的权重与偏置才让组合能作出有区分的判断。

*截图 26|不同权重让一个单元对最终判断的影响更强*
如果一个单元提供的特征更重要,就给它更大的组合权重。权重可以为正、为负或为零,因而既可以支持某种特征,也可以反对或忽略它。训练会根据损失调整这些数值。

*截图 27|实际组合:先算 7×0.7+5×0.8−6,再经过 Sigmoid*
截图给出了一个完整的输出单元:对两个隐藏单元的输出分别乘 $7$ 和 $5$,再减去 $6$。对这个示例点,下一层得到的分数是:
$$
z_{\mathrm{out}}=7\times0.7+5\times0.8-6=2.9.
$$
经过 Sigmoid 后约为 $0.9478$,图中记为 $0.95$。偏置 $-6$ 把分类阈值放到了有意义的位置:某个特征有一点响应,并不意味着最终一定判蓝;两个特征需要合起来提供足够的支持。
## 把区域图重新画成圆点和连线

*截图 28|两个隐藏神经元分别对应两条直线及其概率地图*
图中第一条边界是 $5x-2y=-8$,第二条是 $7x-3y=1$。按正分侧偏蓝的约定,这两个隐藏单元可以写成:
$$
h_1=\sigma(5x-2y+8),\qquad h_2=\sigma(7x-3y-1).
$$
注意结点内的 $-8$ 与 $1$ 是直线等式右边的阈值;移到左边以后,对应偏置分别是 $+8$ 与 $-1$。这是看这组截图时很容易混淆的符号问题。

*截图 29|共享同一组输入,把两个隐藏单元接到同一个输出单元*
把重复画出的 $x,y$ 输入合并,就得到常见的网络图。合并只是改变画法:两个隐藏单元仍然各自用自己的权重处理同一组输入,随后输出单元接收 $h_1,h_2$。
整个例子的前向计算可以写成:
```python
from math import exp
def sigmoid(z):
# 分正负计算,避免很大的负输入使 exp(-z) 溢出。
if z >= 0:
return 1.0 / (1.0 + exp(-z))
e = exp(z)
return e / (1.0 + e)
def predict_blue(x, y):
h1 = sigmoid(5 * x - 2 * y + 8)
h2 = sigmoid(7 * x - 3 * y - 1)
return sigmoid(7 * h1 + 5 * h2 - 6)
```
这段代码复述截图中的给定参数,演示前向计算;它没有执行训练,也不表示这些参数适用于任意数据。

*截图 30|网络结构与区域意义对照:输入坐标、隐藏特征、最终分类区域*
这张是网络的总览图。输入层放原始坐标;隐藏层放从坐标算出的中间特征;输出层给出最终判断。“隐藏”指这些中间响应不是训练数据直接给出的目标标签,而是网络内部计算出的表示。
也可以从这里回答:为什么非要有非线性的激活函数?如果所有层只是乘权重再加偏置,那么无论接多少层,都能合成一次仿射变换;深度不会凭空带来更复杂的分类边界。Sigmoid 等非线性函数让逐层组合真正增加表达能力。
## 更宽、更多输入、更深,分别改变什么

*截图 31|增加隐藏单元:让更多简单特征共同参与判断*
这一层从两个单元扩为三个,相当于允许模型同时利用更多种切分方式。图中三个方向的响应组合后,形成类似圆角三角形的蓝色区域。这是**增加宽度**:同一层拥有更多计算单元。

*截图 32|从两个特征到三个特征:直线对应推广为三维中的平面*
增加输入数量则是另一件事。二维输入是一个平面上的点,三维输入是空间中的点;线性打分为零的地方由直线变成平面。真实任务可以有成百上千个特征,虽然无法直接画出来,计算仍是加权求和再做非线性变换。

*截图 33|增加隐藏层:先组合简单特征,再组合上一层形成的复杂特征*
**深度**说的是层数。第一隐藏层从原始输入计算一些简单特征,后一层组合这些特征,再后一层继续组合,最终可以形成更复杂的边界。
“第一层画线、第二层组合区域”是这段二维示例的直观解释。更深的单元在上一层的表示空间中进行计算,不能把它们全部理解成在原始平面上各画一条直线。更宽或更深也不是效果必然更好;训练数据、优化方法与泛化能力都会影响结果。
## 从坐标点推广到棋盘与图像

*截图 34|围棋:把棋盘局面编码为输入,由网络提供与决策有关的输出*
输入不必是平面坐标,也可以是棋盘局面的编码。输出可以表达落子倾向或局面评价,再与其他算法共同完成决策。截图右侧是用来说明多层网络的结构示意,不能仅凭它就把具体围棋系统的完整实现说成这几层普通全连接网络;实际系统还可能结合卷积、搜索等机制。

*截图 35|自动驾驶:图像像素作为输入,方向或控制量作为输出的教学示例*
自动驾驶示例中,输入来自图像,输出画成左转、右转、前进、后退。这张图强调的是同一条计算路线可以接收别的特征、完成别的任务,并不是完整自动驾驶系统的设计图。
把 35 张截图连起来,可以记住一条主线:先用损失规定什么算好,再让参数沿着减小损失的方向更新;一个神经元把输入转成一个特征或预测,多个单元逐层组合,就能表达更复杂的规律。
本组截图主要讲清了**前向计算与表达能力**。真正训练多层网络时,还需要用链式法则从输出损失向前计算各层参数的梯度,这个过程叫反向传播,再由优化器更新参数。不要把“画出了一个能表达曲线的网络”和“已经把这个网络训练好了”混为一谈。