适用读者:要估算训练需要多少卡/多少显存/多长时间的人;要理解 RL 训练为什么比 SFT 更复杂的工程师。
前置:S23-J10、J11(模型规模与负载)。
覆盖旧文:A-4336 §3.4–§3.6(训练的计算与状态 + RL + 训练与服务预算,245 点)→ 245 点。
扩展点:E-S23-030(训练算力 ≈ 前向 3 倍、总量 ≈ 6ND)、E-S23-031(每参数 18 字节的训练状态账)、E-S23-032(SFT 的损失口径与词表投影陷阱)、E-S23-033(RL 的生成-保留比例与角色依赖)、E-S23-034(Scaling law 的最优分配与两种拟合口径)。
上一篇:S23-J11 · 请求到达、多轮与多模态负载
下一篇:S23-J13 · 加速器:计算单元与存储层次。
1. 一句话结论
训练的三笔账分别是:算力 ≈ 6ND、状态 ≈ 18 字节/参数、激活按生命周期。 第二笔最容易被低估——Qwen3-8B 的训练状态就要 147.433 GB,是推理权重的 9 倍,一张 H100(80 GB)放不下。
出处:AI Infra 教材 §3.4–§3.6(
id 4336)。
算力:F_train ≈ 6·N·D (N 参数、D 训练 token)
状态:18 B / 参数 (BF16 权重 + FP32 梯度 + FP32 主权重 + Adam 两个矩)
激活:前向保留、反向用完即放 (峰值取决于 micro-batch 与重计算策略)
2. 为什么训练是前向的 3 倍(E-S23-030)
对线性层 Y = XW(X:[m,k]、W:[k,n]):
前向: Y = XW → 2mkn FLOPs
输入梯度: dX = dY·Wᵀ → 2mkn
权重梯度: dW = Xᵀ·dY → 2mkn
合计 ≈ 6mkn = 3 × 前向
| 操作 | 要解决的问题 | 为什么还能算 |
|---|---|---|
前向 Y=XW |
求输出 | — |
输入梯度 dX=dY·Wᵀ |
把误差传回前一层 | 需要 W |
权重梯度 dW=Xᵀ·dY |
求这层权重的调整方向 | 需要当时的 X |
"需要当时的 X"就是激活必须保留的原因:前向把结果交出去后,X 不能释放,要等反向用完。
总量近似:F_train ≈ 6·N·D (所有训练 token 都过同一组主要矩阵)
判据:这三项算力相同,所以"训练 = 3 × 推理前向"是个好用的粗算;但要注意边界(见 §7)。
2.1 冻结与稀疏结构怎么算
| 变化 | 省什么 | 不省什么 |
|---|---|---|
| 冻结某权重矩阵 | 它的 dW 计算 |
若更早层仍需梯度,dX 照算 |
| MoE | 只算选中专家的两类梯度 | 路由器与共享分支照算 |
| 注意力 | 按 N_pair 累计 |
投影与 FFN 照算 |
3. 每参数 18 字节(E-S23-031)
| 项 | 精度 | 字节/参数 |
|---|---|---|
| 计算权重 | BF16 | 2 |
| 梯度 | FP32 | 4 |
| 主权重(master weight,高精度更新用) | FP32 | 4 |
| Adam 一阶矩 | FP32 | 4 |
| Adam 二阶矩 | FP32 | 4 |
| 合计 | 18 |
Qwen3-8B 代入(8,190,735,360 参数):
18 × 8,190,735,360 = 147,433,236,480 B = 147.433 GB ≈ 137.308 GiB
对比(原文点名):
| 硬件 | 标称显存 | 放得下吗 |
|---|---|---|
| H100 SXM | 80 GB | ❌ |
| RTX PRO 6000 Blackwell WS | 96 GB | ❌ |
| H200 | 141 GB | ❌ |
判据:训练状态是推理权重的 9 倍,且这还没算激活。 所以"这个模型能推理"绝不等于"这个模型能训练"。
3.1 micro-batch 与激活生命周期
micro-batch:一次前向+反向实际处理的数据子集
累积 a 个 micro-batch → 更新一次参数
激活:该层反向用完即释放(所以峰值由 micro-batch 决定,而非总 batch)
判据:显存不够时,先减 micro-batch、加累积次数,总训练数据量不变;代价是执行顺序与重叠机会变了。
4. SFT:读的 token ≠ 算损失的 token(E-S23-032)
一条 SFT 样本可能包含:系统提示 + 用户问题 + 工具结果 + 回答,但只对回答部分计算损失。
参与主干的 token:全部(都要提供上下文)
参与损失的 token:只有回答部分
陷阱(原文明确):如果只在算损失时屏蔽不参与监督的 token,却没有跳过这些 token 的词表投影,那部分矩阵乘法照常执行。
| 实现方式 | 词表投影成本 |
|---|---|
| 屏蔽损失,但对全部 token 做词表投影 | 按全部 token 计 |
| 只对参与监督的 token 做词表投影 | 按回答 token 计(可省很多) |
判据:SFT 的成本要按"哪部分真正进了损失"算,不能按"序列长度"算。
4.1 长度组成改变注意力开销(同上)
两组独立文档,都含 8,192 token:
| 组成 | 有效因果配对 N_pair |
|---|---|
| 4,096 + 4,096 | 16,781,312 |
| 7,168 + 1,024 | 26,218,496 |
Qwen3-8B 一层上,QKᵀ 与 AV 前向从 0.275 → 0.430 TFLOPs(+56%)——而投影与 FFN 处理的行数完全相同。
判据:同样的 token 总数,"长文档拼接"比"短文档拼接"更贵。 数据配比(packing 策略)会直接改变算力预算。
4.2 一次完整训练步的实测口径(原文数)
Qwen3-8B,B=1, P=8192,全参数、无重计算:
| 矩阵计算 | TFLOPs |
|---|---|
| 前向 | 143.789 |
| 反向 | 287.579 |
比值 ≈ 2.0(反向略高于前向的 2 倍关系,因为注意力等项)。
对照 6ND 粗算(D=8192):6 × 8.19e9 × 8192 = 402.59 TFLOPs,而逐项合计 143.789 + 287.579 = 431.37 TFLOPs——粗算低估约 7%,差额来自注意力配对与词表投影。
5. RL:多角色流水线(E-S23-033)
策略生成(rollout) → 奖励/教师评分 → 学习器更新 → 新权重同步给生成副本
| 角色 | 读什么 | 产什么 | 变慢的后果 |
|---|---|---|---|
| 生成(rollout) | 提示 + 当前权重 | 回答 token | 后续全等 |
| 奖励 / 教师 | 回答(+ 参考答案) | 分数 / 概率分布 | 学习器空转 |
| 学习器 | 保留样本 | 新权重 | 生成副本用旧权重 |
| 环境 / 测试 | 代码、工具 | 可验证反馈 | 评分阶段等待(CPU/沙箱资源) |
5.1 生成量与保留比例
保留 n_keep 条样本、平均保留比例 a
⇒ 需要生成 n_generate ≈ n_keep / a
保留 16 条、a=1/2 → 生成 32 条
a=1/4 → 生成 64 条
判据:保留比例下降,只增加"生成 + 评分"的工作,不会按同比例扩大更新 batch。 采样策略变严,成本涨在流水线前段。
5.2 蒸馏与教师
多教师同策略蒸馏(OPD):学生自己生成轨迹,教师在相同 token 位置给出候选分布;学生据此学习。代价:教师前向成为"生成与更新"之间新增的一项模型工作,还要额外存教师权重。
6. 预算:Scaling law 与最优分配(E-S23-034)
L(N,D) = E + A/N^α + B/D^β
约束:C = 6ND ⇒ D = C/(6N)
最优:N_opt = (αA/(βB))^(1/(α+β)) · (C/6)^(β/(α+β))
含义:左边 = 加参数带来的损失下降,右边 = 减数据造成的损失上升;两者相等时,再微调参数量已无净收益。
两种拟合口径的分歧(原文点名):
| 研究 | 分配关系 | 倾向 |
|---|---|---|
| Kaplan 等(早期) | N ∝ C^0.73、D ∝ C^0.27 |
更多预算给参数 |
| Chinchilla | 参数与数据接近等比例增长 | 更多预算给数据 |
判据:N_opt 只最小化"固定训练预算下的验证损失",不含推理成本、也不看数据供给是否充足。要长期服务大量请求时,最优解会偏向"更小、训练更充分"的模型——这是把训练账和服务账放在一起算的结果。
7. 前提与边界
| 结论 | 成立条件 | 不成立时 |
|---|---|---|
F ≈ 6ND |
稠密、全参数、无重计算 | MoE(只算选中专家)、冻结、重计算 → 逐项算 |
| 18 字节/参数 | BF16 权重 + FP32 梯度/主权重 + Adam | 用 8 位优化器、分片 → 按实际精度算 |
| 反向 = 2 × 前向 | 线性层口径 | 注意力、词表头、非线性 → 逐项补 |
N_opt 可用 |
幂律拟合有效、数据充足 | 数据受限 / 推理为主 → 重新优化 |
8. 常见误区
| 误区 | 纠正 |
|---|---|
| 用推理显存推训练显存 | 差 9 倍(18 B vs 2 B 每参数),还没算激活 |
| 以为冻结就不用算梯度 | 上游层仍需输入梯度 |
| 按序列长度估 SFT 成本 | 只对监督 token 算损失;但注意词表投影有没有跳过 |
| 认为 token 总数相同就等价 | 文档拼接方式改变 N_pair,注意力开销差 56% |
把 N_opt 当部署建议 |
它不含推理成本与数据约束 |
8.1 可复算(实测)
$ cd /root/博客运营官/blog-v2 && python3 tools/s23_book_calc.py | tail -6
Qwen3-8B 训练状态 = 18 B × 8,190,735,360 = 147.433 GB = 137.308 GiB(H100 80 GB 放不下)
N_pair 4096+4096 = 16,781,312;7168+1024 = 26,218,496;增幅 56%
6ND 粗算(D=8192): 402.59 TFLOPs(原文逐项:前向 143.789 + 反向 287.579)
保留 16 条、比例 0.5 → 生成 32 条
保留 16 条、比例 0.25 → 生成 64 条
9. 自测
- Qwen3-8B 全参数训练的"参数相关状态"共多少 GB(18 B/参数)?为什么放不进 H100?
- 同样 8,192 token,
4096+4096与7168+1024的有效配对差多少?为什么? - 保留 32 条样本、保留比例 25%,需要生成多少条?
- Kaplan 与 Chinchilla 的分配差异,落到"同样 10 倍算力"上分别倾向什么?
答案
- 147.433 GB ≈ 137.308 GiB;H100 只有 80 GB,且激活尚未计入。
- 16,781,312 vs 26,218,496(后者多 56%);长文档中每个 token 能看到的更多前文,因果配对更多。
32 / 0.25 = 128条。- Kaplan 倾向把更多预算给参数;Chinchilla 倾向参数与数据等比例增长。
10. 下一篇
S23-J13 · 加速器:计算单元与存储层次 —— 进入第二部分:从模型需求转到执行资源,看计算单元、寄存器/共享内存/HBM 的层次如何决定"能不能喂饱算力"。