Loss & 反向传播
训练神经网络的核心 — 理解损失函数和梯度计算
- 损失函数衡量模型预测与真实标签的差距
- 交叉熵损失是分类任务的标准选择
- 反向传播利用链式法则从输出层向输入层传递梯度
- 梯度下降沿着损失函数的负梯度方向更新参数
什么是损失函数?
损失函数(Loss Function)衡量的是模型的预测和真实答案之间的差距。 差距越大,损失越大;预测越准,损失越小。
类比:就像考试估分 — 你预估自己考 85 分,实际考了 90 分,差距是 5 分。 估分越准,"损失"越小。
训练的目标:通过调整模型参数,让损失函数的值越来越小。 这个过程就是优化。
MSE — 均方误差
用于回归任务(预测连续值)
MSE = (1/n) × Σ(y - ŷ)²
交叉熵 — Cross Entropy
用于分类任务(预测类别概率)
CE = -Σ y × log(p)
📊 MSE 手推:一步一步算
MSE 衡量每个样本的预测值与真实值之差的平方的平均值。点击单元格可编辑数值!
| 样本 | 真实值 y | 预测值 ŷ | 差值 (y - ŷ) | 平方 (y - ŷ)² |
|---|---|---|---|---|
| 样本 1 | 3 | 2.8 | 0.200 | 0.040 |
| 样本 2 | 5 | 5.2 | -0.200 | 0.040 |
| 样本 3 | 7 | 6.5 | 0.500 | 0.250 |
| MSE = 平均 | 0.110 |
✅ 验证:(0.040 + 0.040 + 0.250) / 3 = 0.110 ✓
📊 交叉熵手推:一步一步算
交叉熵衡量预测概率与真实标签之间的差距。当真实标签是 one-hot 编码时,公式简化为 -log(p正确类别)。
| 类别 | 真实标签 (one-hot) | 预测概率 p | -log(p) | y × (-log(p)) |
|---|---|---|---|---|
| 类别 A | 1 | 0.7 | 0.357 | 0.357 |
| 类别 B | 0 | 0.2 | 1.609 | 0.000 |
| 类别 C | 0 | 0.1 | 2.303 | 0.000 |
| 交叉熵 = 求和 | 0.357 | |||
💡 观察:预测概率越接近 1,-log(p) 越小(接近 0),损失越低。当预测正确类别概率为 1 时,交叉熵 = 0。
🔗 链式法则手推
反向传播的核心是链式法则:对于复合函数,梯度可以逐层"传递"回去。这里用一个简单例子 y = (2x + 1)² 来演示。
令 u = 2x + 1,则 y = u²
链式法则:dy/dx = dy/du × du/dx = 2u × 2 = 4u = 4(2x+1)
修改 x 的值,观察梯度如何变化:
| x | u = 2x + 1 | y = u² | dy/du = 2u | du/dx = 2 | dy/dx = 4u |
|---|---|---|---|---|---|
| 2 | 5 | 25 | 10 | 2 | 20 |
| 公式 | =2*A+1 | =B² | =2*B | 常数 | =D×E |
🔗 链式法则:dy/dx = dy/du × du/dx。这就是反向传播的数学基础 — 把梯度从输出层一层一层传回输入层。
🎮 互动实验:学习率的影响
学习率(Learning Rate)决定了每次参数更新的步长。太小收敛慢,太大则震荡甚至发散。
💡 观察:
- • 学习率很小(<0.01):收敛很慢,需要更多迭代
- • 学习率适中(0.01~0.1):平稳下降,快速收敛
- • 学习率较大(0.5~0.8):开始震荡,但仍可收敛
- • 学习率太大(>0.9):损失发散,越来越大!
💻 代码实现 (PyTorch)
import torch
import torch.nn as nn
# MSE Loss — 用于回归任务
mse_loss = nn.MSELoss()
y_true = torch.tensor([3.0, 5.0, 7.0])
y_pred = torch.tensor([2.8, 5.2, 6.5])
loss = mse_loss(y_pred, y_true)
print(f"MSE Loss: {loss.item():.3f}")
# 输出: MSE Loss: 0.110 ✓ 和 Excel 算的一样!
# Cross Entropy Loss — 用于分类任务
ce_loss = nn.CrossEntropyLoss()
# 注意:CrossEntropyLoss 接受 logits(未归一化的分数),不需要先做 softmax
logits = torch.tensor([[2.0, 1.0, 0.1]]) # (batch=1, classes=3)
labels = torch.tensor([0]) # 真实类别是第 0 类
loss = ce_loss(logits, labels)
print(f"Cross Entropy Loss: {loss.item():.3f}")
# 反向传播 — 自动计算梯度
x = torch.tensor([2.0], requires_grad=True)
y = (2 * x + 1) ** 2 # y = (2x+1)² = 25
y.backward() # 反向传播,计算 dy/dx
print(f"dy/dx = {x.grad.item()}")
# 输出: dy/dx = 20.0 ✓ 和 Excel 算的一样!(4u = 4×5 = 20)
📝 总结
损失函数
衡量预测与真实值的差距。MSE 用于回归,交叉熵用于分类。训练目标是让损失越来越小。
链式法则
复合函数的梯度 = 各层梯度的乘积。dy/dx = dy/du × du/dx,这是反向传播的数学基础。
反向传播
利用链式法则,从输出层到输入层逐层计算梯度。PyTorch 的 loss.backward() 自动完成。
学习率
控制参数更新的步长。太小收敛慢,太大震荡发散。需要通过实验找到合适的值。