GOCLAWLLM ENGINEERING
GoClaw 首页

2. 必要数学基础

基础3~5 小时
学习目标
  1. 使用张量形状检查计算
  2. 从 logits 推导 softmax、交叉熵与困惑度
  3. 解释梯度、AdamW 与数值稳定性
前置知识
  • 高中代数
  • 基础 Python

本章产物完成自动微分 Notebook,并手算一个三分类交叉熵例题。

本章只引入分析 LLM 所需的数学与机器学习工具。重点是理解张量、损失、梯度和优化之间的因果关系。

2.1 标量、向量、矩阵和张量

假设:

batch = B
序列长度 = T
隐藏维度 = C
词表大小 = V
注意力头数 = H
每头维度 = D = C / H

那么:

token IDs:  [B, T]
embedding:  [B, T, C]
Q/K/V:      [B, H, T, D]
注意力分数: [B, H, T, T]
logits:     [B, T, V]

读代码时先写形状,往往比盯着 API 更容易找出错误。

2.2 矩阵乘法的含义

如果:

X 的形状是 [B, T, C]
W 的形状是 [C, M]

则:

Y = X @ W
Y 的形状是 [B, T, M]

线性层本质上学习一个从 C 维空间到 M 维空间的映射。注意力中的 Q、K、V 都是同一个输入经过不同线性映射得到。

2.3 点积、相似度和缩放

两个向量点积:

x · y = x_1 y_1 + x_2 y_2 + ... + x_d y_d

当方向更一致时点积通常更大,但点积也受向量长度影响。注意力把 Q 与 K 做点积,得到“当前查询应该关注哪个位置”的匹配分数。

若 Q、K 各维方差约为 1,d 个独立乘积相加后,点积方差会随 d 增大。分数过大时 softmax 接近 one-hot,梯度容易变得很小。因此缩放点积注意力使用:

score = (Q @ K^T) / sqrt(d_k)

除以 sqrt(d_k) 的目的,是让不同 head dimension 下的分数尺度更稳定。

2.4 概率、softmax 和对数

softmax 把任意 logits 变成总和为 1 的概率:

p_i = exp(z_i) / Σ_j exp(z_j)

实际实现会先减去最大 logit,避免指数溢出:

softmax(z) = softmax(z - max(z))

对数把连乘变成连加,数值更稳定:

log(a × b) = log(a) + log(b)

所以语言模型优化的是 log probability,而不是直接把许多很小的概率相乘。

2.5 交叉熵和负对数似然

正确 token 是 y,模型给它的概率是 p_y

单个位置的 loss = -log(p_y)

整个批次通常取所有有效位置 loss 的平均值。softmax 与交叉熵结合后,对 logit 的梯度有一个非常直观的形式:

gradient = predicted_probability - one_hot_target

也就是:错误候选概率太高就往下调,正确候选概率不足就往上调。

2.6 熵、交叉熵与困惑度

困惑度:

perplexity = exp(平均负对数似然)

直觉上,困惑度 10 可以粗略理解为:模型在每一步像是在 10 个同等可能的候选中犹豫。但不同 tokenizer 会改变 token 粒度,因此不同 tokenizer 的 perplexity 不宜直接横向比较。

2.7 导数、梯度和链式法则

导数描述输入变化一点时,输出如何变化。对多参数函数,所有偏导数组成梯度。

若:

y = f(x)
loss = g(y)

链式法则:

d(loss)/dx = d(loss)/dy × dy/dx

反向传播就是从 loss 出发,沿计算图反向重复应用链式法则。

运行:

python code/01_tensor_autograd.py

重点观察:

  1. requires_grad=True 告诉 PyTorch 记录相关计算。
  2. loss.backward() 计算梯度。
  3. 参数更新必须放在 torch.no_grad() 中。
  4. PyTorch 默认累积梯度,所以每轮要清零。

2.8 梯度下降、AdamW 和学习率

最简单的梯度下降:

parameter = parameter - learning_rate × gradient

Adam 会维护梯度的一阶矩和二阶矩,对不同参数自适应调整步长。AdamW 将 weight decay 与梯度更新解耦,是 Transformer 训练的常见优化器。

学习率过大:loss 震荡、发散或出现 NaN。 学习率过小:训练稳定但收敛太慢。

常见 schedule:

Warmup:开始阶段从很小的学习率逐渐升高
Cosine decay:之后按余弦曲线逐渐降低

Warmup 能减少随机初始化或新任务开始时的大梯度冲击。

2.9 监督学习、训练集与泛化

监督学习把样本表示为输入与目标的配对。模型在训练集上最小化经验损失,但工程目标是降低未见样本上的风险。训练损失持续下降而验证损失上升,通常意味着模型开始记忆训练数据中的偶然模式。

LLM 预训练同样可以写成监督学习形式:

输入:token[0:T-1]
目标:token[1:T]

因果遮罩保证位置 t 只能使用此前信息。训练集、验证集和测试集必须在文档级或来源级完成隔离;仅按 token 随机切分会把相邻内容泄漏到不同集合。

2.10 MLP、反向传播与表示能力

单个线性层只能表达线性映射。MLP 在线性层之间加入非线性激活,使网络能够组合更复杂的特征。Transformer Block 中的前馈网络就是逐 token 应用的 MLP:

x → Linear(C, rC) → activation → Linear(rC, C)

反向传播负责计算每个参数对最终损失的贡献,优化器再根据梯度更新参数。两者职责不同:反向传播提供方向,优化器决定步长、动量和正则化方式。

2.11 正则化与数值稳定性

模型容量高于数据约束时,需要通过数据、目标或优化过程抑制过拟合:

数值稳定性同样属于模型正确性。Softmax 通常先减去最大 logit;混合精度训练需要关注溢出、下溢和 loss scaling。

2.12 基础知识的学习边界

《动手学深度学习》适合作为本章的系统参考。与 LLM 主线直接相关的部分包括数据操作、线性代数、自动微分、概率、线性网络、MLP、优化、序列建模、注意力和 Transformer。卷积网络、目标检测等计算机视觉章节可以作为扩展阅读,不作为进入 LLM 工程的前置条件。

配套实验:

2.13 基础题组与答案线索

题 1|矩阵形状。 X:[2,4,8]W:[8,16] 相乘,输出是什么形状?答案线索:矩阵乘法作用于最后一维,batch 与序列维保留。

题 2|稳定 Softmax。 为什么 softmax([1000,1001]) 应先减去 1001?答案线索:减去同一常数不改变概率比,但避免 exp(1001) 溢出。

题 3|交叉熵。 正确类别概率从 0.1 增加到 0.5,NLL 怎样变化?分别计算 -log(0.1)-log(0.5)

题 4|梯度。 y=(wx-b)^2,给定 w=2,x=3,b=5,求 dy/dw。先算误差,再应用链式法则,并与自动微分比较。

题 5|AdamW。 为什么 weight decay 不应简单等同于在 loss 中加入 L2?答案线索:AdamW 把衰减从自适应梯度更新中解耦。

题 6|泛化。 训练 loss 下降、validation loss 上升时,列出数据、容量和优化三个层面的应对方式。

授课时要求学习者先在纸上写形状或数值,再运行 Notebook。只会得到运行结果而不能预测数量级,说明概念尚未形成。

章节验收:独立完成题 1~4;对题 5~6 能说明机制而不是背结论;Notebook 中所有断言通过,并能解释为什么这些断言足以发现一部分而非全部错误。


本章依据

原理性结论以原始论文、官方文档或公开教材为依据。论文中的实验结果只适用于其声明的模型、数据、硬件和评估设置。

  1. 张量、自动微分、概率、优化与注意力的系统基础。

  2. Adam 的一阶矩、二阶矩估计与偏差修正。

  3. AdamW 中权重衰减与损失梯度更新的解耦。

  4. LayerNorm 的定义和训练稳定性背景。