反向传播(Backpropagation) 是训练神经网络的核心算法,它通过反向逐层计算损失函数对每个权重的梯度,来反向逐层更新网络的权重,从而最小化损失函数。
一、反向传播的基本概念
1. 前向传播(Forward Propagation)
在前向传播中,输入数据从输入层通过隐藏层传递到输出层。网络通过层与层之间的连接(即权重)来计算每个节点的输出,最终生成网络的预测结果。
2. 计算损失(Compute Loss)
将网络的预测输出与真实值进行比较,计算损失函数(如均方误差),用来衡量网络的预测输出与真实值的差距。
3. 反向传播(Backward Propagation)
反向传播的过程主要由链式法则驱动。它通过逐层计算误差对权重的偏导数(梯度),从输出层反向传递到隐藏层,再传递到输入层(与前向传播顺序相反),以反向更新每层的权重,减少预测误差。
- 前向传播相当于将输入数据从输入层逐步传递到输出层,得到预测结果。
- 反向传播相当于从输出层开始反向传递误差,更新每一层的权重,使得网络在下次预测时能够减少误差。
4. 权重更新(Weights Update)
使用优化算法(如梯度下降)根据梯度更新权重。使得下一次前向传播时损失函数值减小。
二、反向传播的数学推导
对于一个简单的神经网络,损失函数 L L L 是关于网络输出 y y y 和真实值 t t t 的函数,而网络输出 y y y 又是关于输入 x x x 和权重 w w w 的函数。
通过链式法则,损失函数对权重的梯度可以表示为:
∂ L ∂ w = ∂ L ∂ y ⋅ ∂ y ∂ w \frac{\partial L}{\partial w} = \frac{\partial L}{\partial y} \cdot \frac{\partial y}{\partial w} ∂w∂L=∂y∂L⋅∂w∂y
三、反向传播的图示
图片来源:https://ai.stackexchange.com/questions/31566/different-ways-to-calculate-backpropagation-derivatives-any-difference
- 前向传播(蓝色箭头)负责计算输出预测值(Out)和误差(Err)。
- 反向传播(绿色和红色箭头)从输出误差(Err)开始,将误差逐层传播到隐藏层( a a a)和输入层(X),计算每个权重(W)的梯度,用于后续的权重更新。
四、反向传播的简单计算示例
假设我们有一个简单的两层神经网络:
- 输入层(x):一个节点,输入值为 x x x。
- 隐藏层(a):一个节点,激活函数为 Sigmoid 函数。
- 输出层(y):一个节点,激活函数为线性函数,输出值为 y y y。
网络的权重:
- 输入层到隐藏层的权重: w 1 w_1 w1。
- 隐藏层到输出层的权重: w 2 w_2 w2。
给定以下初始条件:
- 输入 x = 1 x = 1 x=1。
- 目标输出 t = 0 t = 0 t=0。
- 初始权重 w 1 = 0.5 w_1 = 0.5 w1=0.5, w 2 = 0.5 w_2 = 0.5 w2=0.5。
- 学习率 η = 0.1 \eta = 0.1 η=0.1。
步骤1:前向传播
- 计算隐藏层的输入和输出
z = w 1 ⋅ x = 0.5 ⋅ 1 = 0.5 z = w_1 \cdot x = 0.5 \cdot 1 = 0.5 z=w1⋅x=0.5⋅1=0.5
隐藏层的激活输出(使用 Sigmoid 函数):
a = σ ( z ) = 1 1 + e − z = 1 1 + e − 0.5 ≈ 0.6225 a = \sigma(z) = \frac{1}{1 + e^{-z}} = \frac{1}{1 + e^{-0.5}} \approx 0.6225 a=σ(z)=1+e−z1=1+e−0.51≈0.6225
- 计算输出层的输入和输出
y = w 2 ⋅ a = 0.5 ⋅ 0.6225 = 0.3112 y = w_2 \cdot a = 0.5 \cdot 0.6225 = 0.3112 y=w2⋅a=0.5⋅0.6225=0.3112
步骤2:计算损失
使用均方误差(MSE)作为损失函数:
L = 1 2 ( y − t ) 2 = 1 2 ( 0.3112 − 0 ) 2 ≈ 0.0484 L = \frac{1}{2}(y - t)^2 = \frac{1}{2}(0.3112 - 0)^2 \approx 0.0484 L=21(y−t)2=21(0.3112−0)2≈0.0484
步骤3:反向传播
- 计算输出层对权重 w 2 w_2 w2 的梯度
∂ L ∂ w 2 = ∂ L ∂ y ⋅ ∂ y ∂ w 2 \frac{\partial L}{\partial w_2} = \frac{\partial L}{\partial y} \cdot \frac{\partial y}{\partial w_2} ∂w2∂L=∂y∂L⋅∂w2∂y
计算各部分:
- 损失函数对输出 y y y 的导数:
∂ L ∂ y = y − t = 0.3112 − 0 = 0.3112 \frac{\partial L}{\partial y} = y - t = 0.3112 - 0 = 0.3112 ∂y∂L=y−t=0.3112−0=0.3112
- 输出 y y y 对权重 w 2 w_2 w2 的导数:
∂ y ∂ w 2 = a = 0.6225 \frac{\partial y}{\partial w_2} = a = 0.6225 ∂w2∂y=a=0.6225
- 合并计算梯度:
∂ L ∂ w 2 = 0.3112 × 0.6225 ≈ 0.1938 \frac{\partial L}{\partial w_2} = 0.3112 \times 0.6225 \approx 0.1938 ∂w2∂L=0.3112×0.6225≈0.1938
- 计算隐藏层对权重 w 1 w_1 w1 的梯度
∂ L ∂ w 1 = ∂ L ∂ a ⋅ ∂ a ∂ z ⋅ ∂ z ∂ w 1 \frac{\partial L}{\partial w_1} = \frac{\partial L}{\partial a} \cdot \frac{\partial a}{\partial z} \cdot \frac{\partial z}{\partial w_1} ∂w1∂L=∂a∂L⋅∂z∂a⋅∂w1∂z
计算各部分:
- 损失函数对隐藏层输出 a a a 的导数:
∂ L ∂ a = ∂ L ∂ y ⋅ ∂ y ∂ a = ( y − t ) ⋅ w 2 = 0.3112 ⋅ 0.5 = 0.1556 \frac{\partial L}{\partial a} = \frac{\partial L}{\partial y} \cdot \frac{\partial y}{\partial a} = (y - t) \cdot w_2 = 0.3112 \cdot 0.5 = 0.1556 ∂a∂L=∂y∂L⋅∂a∂y=(y−t)⋅w2=0.3112⋅0.5=0.1556
- 隐藏层输出 a a a 对输入 z z z 的导数(Sigmoid 函数导数):
∂ a ∂ z = a ( 1 − a ) = 0.6225 ⋅ ( 1 − 0.6225 ) ≈ 0.2350 \frac{\partial a}{\partial z} = a (1 - a) = 0.6225 \cdot (1 - 0.6225) \approx 0.2350 ∂z∂a=a(1−a)=0.6225⋅(1−0.6225)≈0.2350
- 输入 z z z 对权重 w 1 w_1 w1 的导数:
∂ z ∂ w 1 = x = 1 \frac{\partial z}{\partial w_1} = x = 1 ∂w1∂z=x=1
- 合并计算梯度:
∂ L ∂ w 1 = 0.1556 × 0.2350 × 1 ≈ 0.0365 \frac{\partial L}{\partial w_1} = 0.1556 \times 0.2350 \times 1 \approx 0.0365 ∂w1∂L=0.1556×0.2350×1≈0.0365
步骤4:更新权重
使用梯度下降法更新权重:
- 更新权重 w 2 w_2 w2:
w 2 new = w 2 − η ⋅ ∂ L ∂ w 2 = 0.5 − 0.1 × 0.1938 ≈ 0.4806 w_2^{\text{new}} = w_2 - \eta \cdot \frac{\partial L}{\partial w_2} = 0.5 - 0.1 \times 0.1938 \approx 0.4806 w2new=w2−η⋅∂w2∂L=0.5−0.1×0.1938≈0.4806
- 更新权重 w 1 w_1 w1:
w 1 new = w 1 − η ⋅ ∂ L ∂ w 1 = 0.5 − 0.1 × 0.0365 ≈ 0.4963 w_1^{\text{new}} = w_1 - \eta \cdot \frac{\partial L}{\partial w_1} = 0.5 - 0.1 \times 0.0365 \approx 0.4963 w1new=w1−η⋅∂w1∂L=0.5−0.1×0.0365≈0.4963
步骤5:验证更新后的网络
再次进行前向传播,计算新的输出和损失。
- 新的隐藏层输入和输出
z ′ = w 1 new ⋅ x = 0.4963 ⋅ 1 = 0.4963 z' = w_1^{\text{new}} \cdot x = 0.4963 \cdot 1 = 0.4963 z′=w1new⋅x=0.4963⋅1=0.4963
a ′ = σ ( z ′ ) = 1 1 + e − 0.4963 ≈ 0.6216 a' = \sigma(z') = \frac{1}{1 + e^{-0.4963}} \approx 0.6216 a′=σ(z′)=1+e−0.49631≈0.6216
- 新的输出层输出
y ′ = w 2 new ⋅ a ′ = 0.4806 ⋅ 0.6216 ≈ 0.2988 y' = w_2^{\text{new}} \cdot a' = 0.4806 \cdot 0.6216 \approx 0.2988 y′=w2new⋅a′=0.4806⋅0.6216≈0.2988
- 新的损失
L ′ = 1 2 ( y ′ − t ) 2 = 1 2 ( 0.2988 − 0 ) 2 ≈ 0.0447 L' = \frac{1}{2}(y' - t)^2 = \frac{1}{2}(0.2988 - 0)^2 \approx 0.0447 L′=21(y′−t)2=21(0.2988−0)2≈0.0447
结果分析
更新权重后,损失从 0.0484 减少到 0.0447,说明网络朝着最小化损失的方向更新,模型性能有所提升。