从零到多模态大模型 · 学习笔记
十卷 · 74 章 · 导读与附录
《从零到多模态大模型》学习笔记
读者画像:软件工程大三、代码有基础、DL/CV 零基础、目标多模态大模型方向科研、导师做图像×美术学交叉。 配套《多模态学习路线.md》:路线图是时间表,本笔记是教材。周级执行计划见卷9。
全书学习路径一张图
flowchart LR
V0["卷0 基础篇<br>数学·PyTorch·反向传播<br>训练工程·远程开发"] --> V1["卷1 现代CV<br>CNN→注意力→Transformer<br>ViT·自监督·CLIP·SAM"]
V1 --> V2["卷2 LLM内功<br>BPE·nanoGPT·预训练<br>SFT·LoRA·DPO/GRPO·vLLM"]
V2 --> V3["卷3 多模态理解<br>三条路线·LLaVA复现<br>connector·tokenizer·评测"]
V3 --> V4["卷4 生成模型<br>DDPM→SD→DiT/Flow<br>可控生成·视频·统一模型"]
V4 --> V5["卷5 前沿专题<br>推理RL·数据中心·具身<br>世界模型·3D·Agent·医学"]
V3 -. "并行读" .-> V8["卷8 美术学交叉 ★<br>美术基础·计算美学·风格史<br>看画VLM·数据集·选题库"]
V5 --> V6["卷6 方法论<br>读论文·复现·选题<br>写作·开源·伦理"]
V6 --> V9["卷9 生涯执行<br>周计划·四条路<br>作品集·面试"]
V0 -. "全程伴随" .-> V7["卷7 工程手册<br>显存/OOM·调试案例<br>分布式·部署·数据管线·AI协作"]怎么用这套笔记
- 学练读结合:按执行计划推进,每章末尾有「自测题」和「动手作业」,不写作业等于没学。
- 保持生长:全书 72 章已完结,但它是活文档——发现某章需要加深/有新论文出现/想增补新主题,随时说一声即可定向更新;7.2 调试案例集预留给你的真实踩坑。
- 实践回写:实际训练踩的坑(OOM、NaN、数据对齐错误),让 AI 整理进卷7「工程实战手册」——那是未来最值钱的部分。
- 卷8 随时可读:美术学交叉卷不依赖前置卷,可与卷0 并行读;8.1 第 10 节是和导师谈话的问题清单。
- 速查与图解:附录·术语速查表 支持面试/复习前快速过牌;附录·十卷思维导图 开卷/合卷各看一眼;多个核心章内含 Mermaid 图解与手算案例(0.1/1.2/2.2/2.3/2.6/2.7/3.1/3.2/3.3/4.2/4.4/4.5/5.1/7.1/9.2)。
- 主动自测三件套:交互测验页(20 题点击判分)、Anki 卡组(84 张,间隔重复)、各章自测题——读一章测一章。另有进度追踪 + 专注计时器(本机保存)。
- 导出 PDF:访问 全书打印版 后 Ctrl+P → “另存为 PDF”——全书合并成一个可批注的 PDF(平板友好)。
- 科研衔接件:论文精读包(10 篇核心论文的预读地图)、延伸资源二维码索引、
scripts/目录三个实用工具(数据体检/美术质检/算力估算)、GitHub Pages 一键部署(见仓库 README)。
全书结构(10 卷 · 70 章)
卷0 基础篇——数学与工程底座(零基础起点)
对应执行计划 W1–W6。目标:读懂后续所有章节的公式和代码。
- 0.1 ✅ 数学基础:线性代数·概率·优化(DL视角三合一)
- 0.2 ✅ Python 与 PyTorch 实战
- 0.3 ✅ 神经网络与反向传播从零实现
- 0.4 ✅ 训练工程常识:混合精度、断点续训、调试与监控
- 0.5 ✅ Git / Linux / 远程开发生存包
卷1 深度学习与CV基础
对应 W7–W12。目标:吃透现代CV最小核心,传统内容只留一层底。
- 1.1 ✅ 从 CNN 到 ResNet:卷积时代的遗产
- 1.2 ✅ 注意力机制
- 1.3 ✅ Transformer 逐层拆解:从 Block 到小 GPT
- 1.4 ✅ ViT 与视觉 Transformer 谱系:图像成为 token
- 1.5 ✅ 自监督三巨头:MAE、CLIP、DINO
- 1.6 ✅ CLIP 精读与 zero-shot 评测实操
- 1.7 ✅ SAM 与分割基础模型:提示式视觉
- 1.8 ✅ 检测/分割极简史:知道即可的一章
- 1.9 ✅ 图像形成与相机模型:几何底座
卷2 LLM 内功(最关键的桥梁)
寒假主战场 W13–W20。目标:“能手写、能微调、能部署”。
- 2.1 ✅ 语言模型前史:n-gram → RNN → 注意力
- 2.2 ✅ BPE tokenizer 原理与实现
- 2.3 ✅ GPT 架构工程版:从 TinyGPT 到 nanoGPT
- 2.4 ✅ 预训练:数据、Scaling Law 与稳定性
- 2.5 ✅ SFT 与指令微调实战
- 2.6 ✅ 参数高效微调:LoRA 与 QLoRA
- 2.7 ✅ 对齐技术:RLHF → DPO → GRPO
- 2.8 ✅ 推理优化与 vLLM
- 2.9 ✅ 架构前沿:MoE、长上下文与注意力变体
- 2.10 ✅ 小模型时代的科研机会(1B–7B 甜点区)
卷3 多模态理解(VLM)
W21–W24。目标:复现 LLaVA 式训练,读懂开源双雄。
- 3.1 ✅ 多模态总览:双塔 / 桥接 / 原生融合三条路线
- 3.2 ✅ LLaVA 范式精读与复现
- 3.3 ✅ Connector 设计空间:Flamingo / BLIP-2 / Qwen-VL
- 3.4 ✅ 视觉 tokenizer:VQ-VAE / VQGAN
- 3.5 ✅ 开源双雄精读:Qwen-VL 与 InternVL 系列
- 3.6 ✅ 文档理解与 OCR-free
- 3.7 ✅ 多模态评测体系与陷阱
- 3.8 ✅ VLM 数据案例研读:caption、合成数据、配比
卷4 生成模型
W25–W28。目标:把扩散演化线串成一条河。
- 4.1 ✅ 生成模型地图:AR / VAE / GAN / Diffusion / Flow
- 4.2 ✅ DDPM 原理与从零实现
- 4.3 ✅ 采样器与 Classifier-Free Guidance
- 4.4 ✅ Latent Diffusion 与 Stable Diffusion
- 4.5 ✅ DiT 与 Flow Matching(SD3 / FLUX 的现代化)
- 4.6 ✅ 可控生成:ControlNet / IP-Adapter / 风格 LoRA
- 4.7 ✅ 视频生成:Sora 范式与开源阵营
- 4.8 ✅ 统一模型之争:Chameleon / Transfusion / Janus
- 4.9 ✅ 前沿瞭望:扩散语言模型
卷5 前沿专题(科研选题池)
暑假起按兴趣选读。
- 5.1 ✅ 多模态推理与 RL:当前最热的研究现场
- 5.2 ✅ 数据为中心的 VLM 研究
- 5.3 ✅ 具身智能与 VLA
- 5.4 ✅ 世界模型与空间智能
- 5.5 ✅ 3D 视觉:NeRF → 3DGS → 前馈重建
- 5.6 ✅ 视觉 Agent 与 Computer Use
- 5.7 ✅ AI for Science 与医学影像
- 5.8 ✅ 高效化:蒸馏、量化、剪枝与小模型
卷6 科研方法论
- 6.1 ✅ 如何读论文:三遍法与精读模板
- 6.2 ✅ 如何复现:最小复现方法论
- 6.3 ✅ 如何选题:价值判断、文献扫描与资源匹配
- 6.4 ✅ 如何写作与投稿:从图表到 rebuttal
- 6.5 ✅ 开源贡献指南:用 PR 说话
- 6.6 ✅ 学术诚信与 AIGC 时代的科研伦理
卷7 工程实战手册(随实践持续增补)
- 7.1 ✅ 显存估算速查与 OOM 排查大全
- 7.2 ✅ 训练调试案例集:十大经典翻车与处置
- 7.3 ✅ 分布式训练入门:DDP / FSDP / DeepSpeed
- 7.4 ✅ 推理部署与成本估算
- 7.5 ✅ 数据管线工程:把数据当代码对待
- 7.6 ✅ AI 协作守则:驾驭代码 agent 而不被其驾驭
卷8 视觉 × 美术学交叉 ★对接导师方向
不依赖前置卷。目标:能与导师对话、在交叉带选题。
- 8.1 ✅ 美术学基础:三层框架·色彩·构图·光影·艺术史
- 8.2 ✅ 计算美学:美学评分与偏好奖励模型
- 8.3 ✅ 风格迁移演化史:Gatys → AdaIN → 扩散时代
- 8.4 ✅ 面向艺术的生成:从控制工具到创作系统
- 8.5 ✅ 艺术理解:让 VLM 真正”看懂”一幅画
- 8.6 ✅ AIGC 时代的艺术评价与人类偏好对齐
- 8.7 ✅ 艺术数据集与基准构建:从 WikiArt 到自建
- 8.8 ✅ 文化遗产数字化与数字人文:AI 进博物馆
- 8.9 ✅ 交叉选题库:结合导师方向的 20 个可执行题目
卷9 生涯执行手册
- 9.1 ✅ 九个月周级执行计划(含夏令营材料清单与导师联系模板)
- 9.2 ✅ 保研/考研/留学/就业四条路分析
- 9.3 ✅ 作品集打造与个人品牌:让 GitHub 替你说话
- 9.4 ✅ 实习申请与面试准备:从简历到 offer
进度 · 全书完结(v2.0,2026.10)
- 🎉 74 章正文全部完成,约 24 万字:卷0(5)+ 卷1(9)+ 卷2(10)+ 卷3(8)+ 卷4(9)+ 卷5(8)+ 卷6(6)+ 卷7(6)+ 卷8(9)+ 卷9(4)
- 🔍 已做通篇一致性检查:导航全部有效、章节内链零损坏、无草稿残留(
python check_site.py可随时复查) - 📌 这套笔记是活文档:7.2 调试案例集等你用真实踩坑回填;各章延伸资源里的论文在新发表时按需增补;目录结构调整说一声即可
本周就该做的三件事(按 8.9 选题库)
- 读 8.1 + 8.9,选 top3 题目,给 top1 写一页 proposal;
- 拿着它和 9.1 的模板联系导师(W5–W6 的既定动作);
- 开始 A1 评测集的 v0 标注规范(30 条样例)——全线受益的基础设施。
写作约定
- 公式配直觉解释,所有数学都回答”这在模型里的哪里出现”
- 代码可运行优先,标注版本;每章末尾:自测题(带提示)+ 动手作业 + 延伸资源(≤5 个)
- 观点有争议处标注「业界有分歧」,不装成定论
0.1 数学基础:线性代数 · 概率 · 优化(深度学习视角三合一)
本章目标:不是把你变成数学系学生,而是把后续所有章节会用到的数学一次配齐,并且每个概念都告诉你它在模型里的哪个位置出现。学完标准:能看懂后续所有章节的公式,能自己推导 softmax+交叉熵 的梯度。
1. 为什么学这三样
深度学习里,数学只有三个角色:
| 数学分支 | 角色 | 一句话 |
|---|---|---|
| 线性代数 | 数据的语言 | 图像、文本、特征全都是矩阵/张量,模型就是一连串矩阵变换 |
| 概率与信息论 | 学习的目标 | “训练”= 让模型输出的概率分布逼近真实分布 |
| 优化 | 学习的发生机制 | 沿着梯度下降,把目标变小 |
传统数学课按”定义→定理→证明”推进,我们反过来:先看它在模型里的用法,再回头看定义。
2. 线性代数
2.1 向量与内积:相似度的度量
向量是一列数。内积(点积),几何意义是”对齐程度”:方向越一致,内积越大。
为什么这是最重要的概念:整个多模态大模型都在算内积。
- CLIP 把图像和文本各编码成一个向量,用内积衡量”图文是否匹配”;
- Attention 的核心就是 Query 和 Key 的内积(),内积大 = “这个位置值得注意”;
- 向量数据库检索图片 = 查询向量与百万张图的特征向量算内积。
2.2 矩阵乘法:三种视角
( 是 , 是 )可以同时理解为:
- 变换的复合: 对空间做一次线性变换, 再做一次。神经网络的每一层就是一次变换,100 层网络 = 100 次复合。
- 批量内积: 的第 元 = 的第 行与 的第 列的内积。Attention 矩阵 就是这个视角。
- 加权求和: 的每一列是 的列的线性组合,组合权重来自 。全连接层 就是”用 的行作为权重,混合输入特征”。
三种视角在调试时各有用处。看到矩阵乘法报 shape 错误,先问自己用的是哪个视角。
2.3 范数与距离
- 范数 :欧氏长度,默认选项。
- 范数 :对离群值不敏感,稀疏化时用。
常见用法:权重衰减(weight decay)约束的是权重的 范数;归一化(normalize)把向量除以自己的 范数后,内积就变成了余弦相似度——CLIP 检索、向量库检索都这么做。
2.4 特征分解与 SVD:低秩的世界
SVD(奇异值分解)说:任何矩阵 都可以拆成 ,其中 是对角阵,对角元(奇异值)从大到小排。保留前 个最大奇异值,就能用低秩矩阵近似 。
这在多模态大模型里的出现位置:
- LoRA:微调大模型时不直接更新权重矩阵 ,而是学一个低秩增量 ( 是 , 是 ,)。理论基础就是”微调带来的权重变化近似低秩”。你在路线阶段2就会用它。
- 图像压缩、PCA 降维、推荐系统,本质都是”砍掉小的奇异值”。
2.5 矩阵求导与链式法则
深度学习的”学习”= 对数百万个参数求梯度,然后沿梯度反方向走。你需要的矩阵求导其实只有一条规则:
链式法则:,则 。多变量的情况就是把雅可比矩阵相乘——这就是”反向传播”的全部数学。
必会推导:softmax + 交叉熵的梯度 = 预测 − 标签
softmax 把任意分数向量 变成概率分布:。 交叉熵损失:,其中 , 是 one-hot 标签。
直接对 求导(过程略,建议自己推一遍,用到的只有链式法则和 ),结论:
为什么这个结论是深度学习里最重要的一行公式:梯度恰好是”预测概率分布减去真实分布”。模型错得越离谱,梯度越大——学习的方向自动就是”把概率从错误的类挪到正确的类”。语言模型预测下一个 token、VLM 回答问题,输出的都是这个形式。你以后看到 loss = cross_entropy(logits, labels),脑子里应该浮现 p − t。
3. 概率与信息论
3.1 速通核心概念
- 随机变量与分布:图像分类模型输出 ,就是一个分类分布(categorical distribution)。
- 条件概率 :给定输入图像 ,输出标签 的概率。监督学习学到的就是这个——所以分类模型叫”判别式”,生成模型学 或 ,叫”生成式”。扩散模型和 GPT 都是生成式。
- 期望与方差:随机初始化下 loss 的波动、batch 之间的梯度噪声,都用它们来描述。
3.2 极大似然:训练到底在干嘛
给定数据 和带参数 的模型 ,极大似然估计(MLE)就是选 让数据出现的概率最大:
右边就是”最小化负对数似然(NLL)“——你训练过的每一个模型的损失函数,几乎都是它换个名字:
- 分类任务的交叉熵 = NLL;
- 语言模型”预测下一个 token”= 对下一个 token 的 NLL;
- 扩散模型预测噪声的 MSE = 高斯假设下 NLL 的简化版。
建立这个等式感:以后看到任何奇怪的 loss,第一反应问”它是谁的负对数似然”。
3.3 熵、交叉熵、KL 散度
- 熵 :分布的不确定性。均匀分布熵最大。
- 交叉熵 :用 编码真实分布 的代价。训练时 是数据/标签, 是模型输出。
- KL 散度 :两个分布的差异。 固定时,最小化交叉熵 = 最小化 KL。
出现位置:
- 知识蒸馏:让学生的输出分布逼近老师的(KL);
- DPO / RLHF:约束微调后的模型别偏离原模型太远(KL 惩罚);
- VAE:后验分布逼近标准正态(KL)。
一句话:交叉熵管”学什么”,KL 管”别学歪”。
3.4 softmax 与温度
里的 是温度: 逼近取最大值(独断), 大则分布平坦(犹豫)。出现位置:LLM 采样时的 top-p/top-k 温度参数;蒸馏时高温让老师的”暗知识”(次优选项的相对概率)显现。
4. 优化
4.1 损失曲面的高维直觉
参数量上亿的模型,损失曲面在高维空间里。高维空间的重要事实:真正的”局部极小值”很少,绝大多数驻点是鞍点——某些方向向上、某些方向向下,总能找到出路。所以不用担心”卡在局部最优”,实际问题是”下降太慢”和”震荡”。
4.2 从 SGD 到 AdamW
- SGD:沿当前 batch 的梯度走一小步。问题:不同参数的梯度尺度差异大,一个学习率伺候不了一堆参数。
- Momentum:积累历史梯度方向,冲过小沟坎。
- Adam:为每个参数自适应缩放步长(除以梯度的一阶/二阶动量)。现代默认。
- AdamW:修复了 Adam 中 weight decay 与自适应步长耦合的 bug,把权重衰减解耦出来。现在所有 LLM/VLM 训练默认都是 AdamW,你只需要记住这个名字和”decay 系数一般 0.01~0.1”。
4.3 学习率:最重要的单一超参
现代默认配方:warmup + cosine decay。前 1~5% 步数从 0 线性升到峰值(大模型早期梯度方向不可信,直接大步会崩),然后余弦缓降到接近 0。
经验参考值:从零训小模型峰值 1e-3 量级;微调 7B 用 LoRA 峰值 1e-4 ~ 2e-4;全参数微调大模型 1e-5 量级。微调的学习率几乎总比预训练小 10~100 倍——别把人家学好的东西一脚踢翻。
4.4 Batch size 与梯度累积
大 batch 梯度更稳但单步更贵,且一般认为大 batch 要配大学习率(线性缩放法则,够用即可不必深究)。显存不够时用梯度累积:小 batch 算多次梯度,攒够了再更新一步,等效于大 batch。LoRA 微调 7B 时你几乎一定会用到它。
4.5 过拟合与正则化
- 现象:训练 loss 降、验证 loss 升。数据少 + 模型大 + 训练久 = 必然。
- 手段按优先级:更多/更好的数据 > 数据增强 > weight decay/dropout > 早停。
- 微调场景的特殊性:数据只有几千条时,与其调正则,不如减 epoch、降学习率、用 LoRA。
4.6 训练曲线诊断速查表(先背下来)
| 症状 | 最可能原因 | 处置 |
|---|---|---|
| loss 一开始就 NaN | 学习率过大 / 数据有坏样本 / fp16 溢出 | 降 lr,跳数数据,换 bf16 |
| loss 降到 0.69 附近卡住(二分类) | 模型输出对称、学了个寂寞:标签错了或数据无信号 | 查标签对齐 |
| 训练 loss 降、验证 loss 升 | 过拟合 | 减 epoch、加数据、加正则 |
| loss 剧烈锯齿 | batch 太小或 lr 太大 | 梯度累积、降 lr |
| loss 平台期很久 | lr 太小 / warmup 太长 / 模型容量不够 | 升 lr、查瓶颈 |
5. 自测十题(答案提示在括号里)
- 两个单位向量的内积最大是多少?此时几何关系是什么?(1;同向)
- 为什么归一化后内积 = 余弦相似度?( 时 )
- 一个 的权重矩阵,LoRA 取 ,参数量从多少降到多少?(16.8M → 131K,两个矩阵 )
- 里, 的一行和 的一行分别是什么?(一个 query 向量、一个 key 向量;结果是注意力分数)
- 为什么交叉熵可以写成”负对数似然”?(对 one-hot 标签,,即真实类的对数概率取负)
- 熵为 0 的分布是什么?(one-hot,完全确定)
- KL(p‖q) 和 KL(q‖p) 一样吗?不对称会带来什么行为差异?(不一样;前者在 q 概率低处惩罚重——“宁可信其有”,后者在 p 概率低处惩罚重——“宁可漏掉”。蒸馏里两种选择行为不同,是活跃的研究细节)
- AdamW 和 Adam 的区别一句话?(weight decay 从梯度自适应缩放里解耦出来)
- 微调时学习率应该比预训练大还是小?为什么?(小;预训练权重是好解,只做局部修整)
- 梯度累积解决什么问题?代价是什么?(显存不够模拟大 batch;代价是单位样本耗时几乎不变但每步更慢、BN/LN 统计与真大 batch 有细微差异)
6. 动手作业
- 用 NumPy 手写 softmax 和交叉熵,并用第 2.5 节结论 写出梯度函数,再数值验证(随机小扰动下 )。
- 用 NumPy 对一个随机 矩阵做 SVD,分别保留前 5/20/50 个奇异值重构,算重构误差随秩的下降曲线。这就是”LoRA 为什么可行”的直观感受。
图解 · 数学地图与一次手算
flowchart LR
A["线性代数:数据的语言"] --> A1["内积 → CLIP 相似度 / 检索"]
A --> A2["QKᵀ → Attention 打分"]
A --> A3["SVD / 低秩 → LoRA"]
B["概率与信息论:学习的目标"] --> B1["交叉熵 = 负对数似然<br>一切训练目标"]
B --> B2["KL 散度 → DPO / 蒸馏的缰绳"]
B --> B3["softmax 温度 → 采样与蒸馏"]
C["优化:学习的发生机制"] --> C1["AdamW + warmup/cosine<br>所有现代训练"]
C --> C2["6ND → 任何实验的算力预算"]案例:手算一次 softmax + 交叉熵
设三类 logits ,真实类为第 0 类()。
第一步 softmax:,总和 8.757, 故 。
第二步 loss:。
第三步梯度:。
读出三件事:① 正确类的梯度为负——下一步要抬高它的 logit;② 两个错误类按”谁错得离谱谁多分”,分摊了挪走概率的任务;③ 所有分量之和为 0(概率守恒)。以后你在任何训练日志里看到交叉熵,背后都是这三个数字在动。
7. 延伸资源
- 3Blue1Brown《线性代数的本质》《微积分的本质》(B 站官方翻译版)——直觉构建第一名
- 《Mathematics for Machine Learning》(Deisenroth 等,免费电子版)——按需查阅,不必通读
- Karpathy《The spelled-out intro to neural networks》——把本章数学第一次和代码接起来
0.2 Python 与 PyTorch 实战:从装环境到手写训练循环
本章目标:搭建可用的 GPU 开发环境,把 PyTorch 五大件(张量/autograd/nn.Module/DataLoader/训练循环)全部打通,最后给出一份完整可运行的 CIFAR-10 训练脚本。学完标准:能独立写出一个完整的图像分类训练项目,能自己估算显存。
1. 环境(一次配好,少踩三天坑)
推荐用 uv(快)或 conda(稳)管理环境:
# 方式一:uv(推荐,快)
uv venv --python 3.11 && uv pip install torch torchvision --index-url https://download.pytorch.org/whl/cu124
uv pip install wandb tqdm numpy matplotlib jupyter
# 方式二:conda
conda create -n dl python=3.11 -y && conda activate dl
pip install torch torchvision --index-url https://download.pytorch.org/whl/cu124
验证 GPU 可用(没有 NVIDIA 卡也没关系,本卷所有代码 CPU 能跑,只是慢;租卡见第 8 节):
import torch
print(torch.__version__, torch.cuda.is_available())
print(torch.cuda.get_device_name(0) if torch.cuda.is_available() else "CPU only")
2. 张量:形状操作是 80% 的日常
2.1 创建与基本属性
import torch
x = torch.randn(2, 3, 224, 224) # 常见图像 batch:N×C×H×W
x.shape, x.dtype, x.device, x.requires_grad
2.2 图像相关:NCHW 与形状变换(必背)
图像张量约定为 NCHW(batch, channel, 高, 宽)。RGB 图在 PIL/NumPy 里通常是 HWC,进模型前要转 CHW。
img = torch.randn(224, 224, 3) # HWC
img = img.permute(2, 0, 1) # → CHW,注意 permute 不移动内存,只改"索引方式"
img = img.contiguous() # 需要真实重排内存时才调用
batch = img.unsqueeze(0) # → NCHW,在前面加一维
reshape / view / permute 的区别(面试和 debug 双高频):
view:不复制数据,要求内存连续,快;reshape:能 view 就 view,不行就复制;permute/transpose:交换维度顺序,只改索引,之后常需要contiguous。
2.3 广播(broadcasting):省代码也埋大坑
形状不同也能算,规则是从最后一维向前对齐,缺的或为 1 的维度自动复制:
mean = torch.tensor([0.485, 0.456, 0.406]).view(1, 3, 1, 1) # ImageNet 通道均值
img = (img - mean) / torch.tensor([0.229, 0.224, 0.225]).view(1, 3, 1, 1)
大坑:(N, 3, 224, 224) 和 (3, 224) 相加会广播成 N 份同样的操作(正确);但 (N, 224, 224, 3) 和 (3,) 相加会把 3 广播到 W 维——shape 看似能算,语义完全错了且不报错。广播 bug 的特征:loss 能下降但结果莫名其妙。防法:关键操作前 assert x.shape == 期望形状。
2.4 dtype 与显存
| dtype | 字节/元素 | 用途 |
|---|---|---|
| fp32 | 4 | 训练的主权重、数值基准 |
| fp16 | 2 | 混合精度(有溢出风险,需 loss scale) |
| bf16 | 2 | 混合精度首选(指数位与 fp32 同宽,不易溢出,现代 GPU 默认) |
| int8/int4 | 1/0.5 | 推理量化 |
同一模型,dtype 换一半,显存减一半——这是后面所有显存估算的底层常数。
3. autograd:自动求导
w = torch.randn(3, requires_grad=True)
loss = (w * torch.tensor([1.0, 2.0, 3.0])).sum()
loss.backward()
print(w.grad) # = [1, 2, 3],链式法则自动算出
三条纪律:
- 更新参数用
with torch.no_grad():包住(否则梯度历史越滚越大); - 每个 iteration 开头
optimizer.zero_grad()(PyTorch 默认累加梯度); - 推理用
with torch.inference_mode():,比 no_grad 更省。
4. nn.Module:模型的容器
import torch.nn as nn
class TinyNet(nn.Module):
def __init__(self):
super().__init__()
self.net = nn.Sequential(
nn.Flatten(),
nn.Linear(3 * 32 * 32, 256), nn.ReLU(),
nn.Linear(256, 10),
)
def forward(self, x):
return self.net(x)
要点:__init__ 里赋值为 nn.Module 的属性会自动注册参数;model.state_dict() / load_state_dict() 是存取权重的标准方式(存 .pth 文件);model.to("cuda") 把参数搬到 GPU;model.train() / model.eval() 切换 dropout/batchnorm 行为——评估忘切 eval 是经典 bug。
5. Dataset 与 DataLoader
from torch.utils.data import Dataset, DataLoader
from torchvision import datasets, transforms
tf = transforms.Compose([
transforms.RandomHorizontalFlip(), # 数据增强:只对训练集
transforms.ToTensor(),
transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225]),
])
train_set = datasets.CIFAR10("data", train=True, download=True, transform=tf)
train_loader = DataLoader(train_set, batch_size=128, shuffle=True,
num_workers=4, pin_memory=True, drop_last=True)
num_workers(多进程读数据)和 pin_memory(锁页内存加速传输)是两条免费性能;drop_last=True 丢掉不满的最后一个 batch,避免训练末尾统计失真。
6. 完整训练脚本(逐段精读版)
下面是你要吃透的第一个完整项目。核心训练循环的模式,从 CIFAR 上的小 CNN 到微调 7B 的 VLM,结构完全一样:取数据 → 前向 → 算 loss → 反向 → 更新。
import torch, torch.nn as nn, time
from torch.utils.data import DataLoader
from torchvision import datasets, transforms
torch.manual_seed(0) # 可复现
device = "cuda" if torch.cuda.is_available() else "cpu"
tf_train = transforms.Compose([
transforms.RandomCrop(32, padding=4),
transforms.RandomHorizontalFlip(),
transforms.ToTensor(),
transforms.Normalize([0.485, 0.456, 0.406], [0.229, 0.224, 0.225])])
tf_test = transforms.Compose([
transforms.ToTensor(),
transforms.Normalize([0.485, 0.456, 0.406], [0.229, 0.224, 0.225])])
train_ds = datasets.CIFAR10("data", True, download=True, transform=tf_train)
test_ds = datasets.CIFAR10("data", False, download=True, transform=tf_test)
train_ld = DataLoader(train_ds, 256, shuffle=True, num_workers=4, pin_memory=True, drop_last=True)
test_ld = DataLoader(test_ds, 512, shuffle=False, num_workers=2, pin_memory=True)
class ConvBlock(nn.Sequential):
def __init__(self, cin, cout):
super().__init__(
nn.Conv2d(cin, cout, 3, padding=1, bias=False),
nn.BatchNorm2d(cout), nn.ReLU(inplace=True))
class Net(nn.Module):
def __init__(self, ch=64):
super().__init__()
self.features = nn.Sequential(
ConvBlock(3, ch), ConvBlock(ch, ch), # 32×32
nn.MaxPool2d(2), # 16×16
ConvBlock(ch, ch*2), ConvBlock(ch*2, ch*2),
nn.MaxPool2d(2), # 8×8
ConvBlock(ch*2, ch*4),
nn.AdaptiveAvgPool2d(1)) # 全局平均池化 → 1×1
self.head = nn.Linear(ch*4, 10)
def forward(self, x):
x = self.features(x).flatten(1)
return self.head(x)
model = Net().to(device)
opt = torch.optim.AdamW(model.parameters(), lr=1e-3, weight_decay=0.05)
sched = torch.optim.lr_scheduler.CosineAnnealingLR(opt, T_max=20) # 20 epoch
scaler = torch.amp.GradScaler(enabled=(device == "cuda")) # AMP 混合精度
for epoch in range(20):
model.train(); t0 = time.time()
for step, (x, y) in enumerate(train_ld):
x, y = x.to(device, non_blocking=True), y.to(device, non_blocking=True)
with torch.autocast("cuda", dtype=torch.bfloat16, enabled=(device=="cuda")):
logits = model(x)
loss = nn.functional.cross_entropy(logits, y)
opt.zero_grad(set_to_none=True)
scaler.scale(loss).backward()
scaler.step(opt); scaler.update()
if step % 50 == 0:
print(f"ep{epoch} step{step} loss={loss.item():.3f} lr={sched.get_last_lr()[0]:.2e}")
sched.step()
model.eval(); correct = total = 0 # 每 epoch 评估一次
with torch.inference_mode():
for x, y in test_ld:
x, y = x.to(device), y.to(device)
correct += (model(x).argmax(1) == y).sum().item(); total += y.size(0)
print(f"[ep{epoch}] test acc={correct/total:.4f} time={time.time()-t0:.0f}s")
torch.save(model.state_dict(), f"ckpt_ep{epoch}.pth") # checkpoint
这个脚本里藏着本章所有知识点:种子、设备、数据增强、AMP(autocast 包前向 + GradScaler 包反向)、zero_grad、调度器、train/eval 切换、inference_mode、checkpoint。把它跑通、改坏、修好各一遍,PyTorch 就入门了。
(建议接 wandb:wandb.init(project="cifar") 后把 loss/acc wandb.log() 上去,实验管理习惯从此建立。)
7. 显存速算与 OOM 三板斧
7.1 训练显存速算(全参数、AdamW、fp16/bf16 混合精度)
其中 是参数量。粗算约 16 字节/参数 + 激活,所以:
- 7B 模型全参数训练 ≈ 16×7GB ≈ 112GB+激活 → 单张消费级卡不可能,要 FSDP/DeepSpeed(卷7详述);
- 7B 模型 LoRA 微调:冻结主干,只训 ~0.1% 参数 → 权重 14GB + 少量梯度和优化器状态 ≈ 24GB 卡(4090)正好能跑。这就是为什么”学生甜点区”是 LoRA + 7B/4B 模型。
7.2 OOM 三板斧(按顺序试)
- 降 batch size,配梯度累积补等效 batch;
- 开
gradient_checkpointing(用重算换显存,速度约慢 30%); - 检查是否忘了
torch.no_grad()/inference_mode(),或把整段历史 logits 攒进了 list(日志里loss.item()要立刻取标量,别存 tensor)。
8. 学生算力方案
- 免费:Kaggle(每周约 30h GPU)、魔搭 ModelScope 免费算力、Colab 免费档;
- 租用:AutoDL / 仙宫云,4090 约 1.5–2 元/小时,LoRA 微调一个 7B 跑几小时就是一杯奶茶钱;
- 本地无卡:卷0、卷1 全部内容 CPU 或免费档即可完成,训练类实验攒到租卡时段集中跑。
9. 自测题
view和reshape什么时候行为不同?(内存不连续时:view 报错,reshape 复制)- HWC 转 CHW 该用 view 吗?(不该,维度语义变了要用 permute;view 只能拆并相邻的内存维度)
optimizer.zero_grad()忘写会怎样?(梯度跨 step 累加,loss 不降甚至爆炸)- eval 忘切会怎样?(dropout/BN 用训练行为,测试精度异常波动)
- bf16 比 fp16 好在哪?(指数位同 fp32,动态范围大,不需要 loss scale,几乎不会溢出)
- 为什么
loss.item()而不是把 loss tensor 存进列表?(存 tensor 会保留整张计算图,显存爆) - batch size 减半后想保持等效更新,两个办法?(梯度累积 2 步;或调 lr)
- 一个 3B 模型 fp16 权重占多少显存?加 AdamW 训练状态呢?(6GB;约 3×8+4=28GB 起步,还没算激活)
10. 动手作业(对应路线阶段0里程碑)
- 跑通第 6 节脚本,记录最终精度(ConvBlock 结构约 87–91%)。
- 把
Net换成torchvision.models.resnet18(num_classes=10),加更多增强(trivialaugment),目标:CIFAR-10 测试精度 ≥ 93%。这一步会逼你读懂 torchvision 源码。 - 接入 wandb,画出 loss/lr/acc 三条曲线;故意把 lr 设成 0.1 观察发散,再设 1e-5 观察学不动——亲手建立第 4.6 节速查表的手感。
- 手写一个自定义
Dataset:从文件夹读图片(ImageFolder之外自己实现__getitem__),这是后面做 VLM 数据 pipeline 的地基。
11. 延伸资源
- PyTorch 官方教程《60 Minute Blitz》→《Training a Classifier》——和本章互补
- Karpathy《Let’s build GPT from scratch》前 20 分钟——张量操作的真实工程用法
- 《Dive into Deep Learning》(动手学深度学习)中文版第 2–4 章——系统查漏
0.3 神经网络与反向传播:从零实现(micrograd 路线)
本章目标:不借助 PyTorch 的 autograd,亲手造一个能自动求导、能训练的最小神经网络引擎。学完标准:别人问你”反向传播到底在干嘛”,你能用代码+一行数学回答,而不是背口诀。 本章跟着 Karpathy《The spelled-out intro to neural networks and backpropagation: building micrograd》食用效果最佳——本笔记补足其中的数学直觉和中文讲解。
1. 一个神经元:线性 + 非线性
神经元 = 加权求和 + 偏置 + 激活函数:
激活函数 必不可少:如果不用非线性激活,多层线性变换的复合还是线性变换(),100 层等价于 1 层。非线性是深度的来源。
常用激活:ReLU(,CNN 时代默认)、GELU(Transformer 默认)、tanh(教学常用,光滑好求导)。
2. 计算图:反向传播的舞台
任何计算(比如 loss)都能画成一张有向无环图:输入和参数是叶子,运算符是中间节点,loss 是根。反向传播 = 把链式法则自动化在这张图上:
- 前向:从叶子到根,算出每个节点的值;
- 反向:从根到叶子,用链式法则把”loss 对每个节点的梯度”逐层乘回去。
关键直觉:每个节点只需知道两件事——(a) 它怎么由输入算出(局部前向公式);(b) 它的输出梯度怎么分摊给各输入(局部梯度公式)。局部规则 + 全局调度 = 自动求导。PyTorch 的 autograd 干的就是这件事,只是规模大、优化多。
3. 必须亲手推一遍的梯度
以两层网络 + softmax + 交叉熵为例(符号与 0.1 章 §2.5 一致):
前向:,,,。
反向(从后往前,每步只用链式法则):
- (0.1 章推导过;tanh 的导数是 )
- ,
- (注意转置:误差从上层”倒着流回来”)
- ( 是逐元素乘,激活导数逐点作用)
- 的梯度同第 2 步模式。
观察结构:每层都是”上游梯度 × 本层局部导数,再往上传”。这就是为什么框架只需要每个算子定义 backward(),任意深度的网络都能自动求导。
4. 从零造引擎:micrograd 式实现
4.1 标量自动求导引擎(约 60 行,核心中的核心)
import math
class Value:
"""一个数 + 它的计算历史 + 自动求导能力"""
def __init__(self, data, _children=(), _op=""):
self.data = data
self.grad = 0.0 # d(loss)/d(self)
self._backward = lambda: None
self._prev = set(_children) # 计算图的前驱
self._op = _op
def __add__(self, other):
other = other if isinstance(other, Value) else Value(other)
out = Value(self.data + other.data, (self, other), "+")
def _backward(): # 加法:梯度原样传给两边
self.grad += out.grad
other.grad += out.grad
out._backward = _backward
return out
def __mul__(self, other):
other = other if isinstance(other, Value) else Value(other)
out = Value(self.data * other.data, (self, other), "*")
def _backward(): # 乘法:交换律式分摊
self.grad += other.data * out.grad
other.grad += self.data * out.grad
out._backward = _backward
return out
def tanh(self):
x = self.data
t = (math.exp(2*x) - 1) / (math.exp(2*x) + 1)
out = Value(t, (self,), "tanh")
def _backward(): # d(tanh)/dx = 1 - tanh²
self.grad += (1 - t**2) * out.grad
out._backward = _backward
return out
def backward(self):
# 拓扑排序:保证先算完所有下游,再算自己
topo, visited = [], set()
def build(v):
if v not in visited:
visited.add(v)
for c in v._prev: build(c)
topo.append(v)
build(self)
self.grad = 1.0 # d(loss)/d(loss) = 1
for node in reversed(topo): # 从根往叶子走
node._backward()
# 语法糖
__rmul__ = __mul__
def __neg__(self): return self * -1
def __sub__(self, other): return self + (-other)
def __truediv__(self, other): return self * other**-1
def __pow__(self, k):
out = Value(self.data ** k, (self,), f"**{k}")
def _backward(): self.grad += k * self.data ** (k-1) * out.grad
out._backward = _backward
return out
def __repr__(self): return f"Value({self.data:.4f}, grad={self.grad:.4f})"
读代码时盯住三个设计:
+=而不是=:一个变量被多次使用时(比如c = a + a),梯度要累加()。漏掉累加是最经典的自动求导 bug;_backward存在节点上而不是立刻执行:因为要等所有下游节点贡献完梯度才能跑;backward()里拓扑排序 + 逆序执行:这就是”反向”二字的实现。
4.2 用它搭 MLP 并训练(完整可运行)
import random
random.seed(0)
class Neuron:
def __init__(self, nin):
self.w = [Value(random.uniform(-1, 1)) for _ in range(nin)]
self.b = Value(0.0)
def __call__(self, x):
act = sum((wi*xi for wi, xi in zip(self.w, x)), self.b)
return act.tanh()
class Layer:
def __init__(self, nin, nout):
self.neurons = [Neuron(nin) for _ in range(nout)]
def __call__(self, x):
out = [n(x) for n in self.neurons]
return out[0] if len(out) == 1 else out
class MLP:
def __init__(self, nin, nouts): # 如 [2, 8, 8, 1]
sizes = [nin] + nouts
self.layers = [Layer(sizes[i], sizes[i+1]) for i in range(len(nouts))]
def __call__(self, x):
for layer in self.layers: x = layer(x)
return x
def train_step(model, x, y_target, lr=0.05):
y_pred = model(x) # 前向
loss = (y_pred - y_target) ** 2 # MSE(用我们的引擎算!)
for p in model.parameters(): p.grad = 0.0 # 手动 zero_grad(和 PyTorch 纪律一致)
loss.backward() # 自动求导
for p in model.parameters(): # 梯度下降
p.data -= lr * p.grad
return loss.data
model = MLP(2, [8, 8, 1])
model.parameters = lambda: [p for l in model.layers for n in l.neurons
for p in n.w + [n.b]]
# 玩具任务:判断点在圆内还是圆外
data = []
for _ in range(200):
x, y = random.uniform(-1, 1), random.uniform(-1, 1)
data.append(([x, y], 1.0 if x*x + y*y < 0.5 else -1.0))
for step in range(200):
losses = [train_step(model, x, y) for x, y in random.sample(data, 20)]
if step % 20 == 0:
acc = sum((model(x).data > 0) == (y > 0) for x, y in data) / len(data)
print(f"step {step:3d} loss {sum(losses)/len(losses):.4f} acc {acc:.2%}")
跑起来你会看到 loss 下降、acc 爬升——这是你亲手从数学造出来的学习,里面没有一行 PyTorch。
4.3 验证正确性:数值梯度
自动求导写错了不报错,只会”学得慢”。验证方法是对拍:用定义 数值算梯度,和引擎的 grad 对比。PyTorch 里对应 torch.autograd.gradcheck。养成对新写的梯度代码做数值对拍的习惯——这是你区别于”纯 vibe coder”的第一个标志。
5. 初始化:为什么一开始就”该差不多”
若权重全零或方差过大,信号会逐层衰减/爆炸。经验规则:
- He 初始化(ReLU 配套):
- Xavier(tanh/sigmoid 配套):
现代大模型初始化的要点其实就一句话:让每一层输出的方差和输入大致相同。残差连接的层常乘一个 0.02~0.1 的小系数(GPT 做法),让训练初期网络接近恒等映射。
6. Normalization:从 BatchNorm 到 RMSNorm
问题:深层网络里,前面层的参数一变,后面层看到的输入分布就漂移,训练不稳。
- BatchNorm:对每个通道,用 batch 内统计量做标准化 + 可学习的缩放平移。CNN 时代标配。缺点:依赖 batch 统计(推理时要用训练期累计的滑动平均),batch 小时不稳。
- LayerNorm:对每个样本自己的所有特征做标准化,与 batch 无关。Transformer 标配。
- RMSNorm:LayerNorm 的简化——只除以均方根、不减均值,少一半计算。LLaMA/Qwen 系全部用它。省掉的均值中心化被证明基本无害,这是”简单方法赢了”的又一例。
卷2 拆 GPT 架构时会再见到 RMSNorm;现在只需要知道它的位置(每个子层前,Pre-Norm)和动机(稳定深层训练)。
7. NumPy ↔ 引擎 ↔ PyTorch 概念映射表
| 概念 | 本章引擎 | PyTorch |
|---|---|---|
| 带梯度的数 | Value | tensor(requires_grad=True) |
| 前向计算 | 重载运算符 | 一切 tensor 运算 |
| 反向传播 | backward() 拓扑逆序 | loss.backward() |
| 清梯度 | p.grad = 0 | optimizer.zero_grad() |
| 参数集合 | model.parameters() | model.parameters() |
| 梯度下降 | p.data -= lr*p.grad | optimizer.step() |
你会发现第 0.2 章的训练循环和 4.2 节的训练循环逐行同构。从此 PyTorch 对你不再是黑盒。
8. 自测题
- 为什么
__add__的_backward里用+=?举一个会出错的场景。(c = a + a;共享节点梯度叠加) - 加法的反向传播是什么形式?乘法呢?(恒等分摊给两边;交叉乘对方的值)
- 为什么拓扑排序必须”逆序”执行
_backward?(梯度依赖下游已算完,loss 是根,逆拓扑 = 从根到叶) - tanh 导数在 |x| 很大时趋近多少?这对梯度意味着什么?(0;饱和区梯度消失,GELU/ReLU 缓解此问题)
- 为什么全零初始化会让”对称神经元”永远一样?(同层神经元收到相同梯度,永远同步更新,网络等效宽度 1)
- BatchNorm 和 LayerNorm 的统计维度差在哪?为什么 LLM 用后者?(BN 沿 batch 维统计、LN 沿特征维;LLM 序列长度可变且 batch 小,且推理不依赖滑动统计)
- RMSNorm 砍掉了什么?为什么基本无害?(减均值;特征均值信息弱,且残差流本身提供中心化)
- 数值梯度的公式是什么? 太大会怎样、太小会怎样?(中心差分;太大截断误差、太小浮点舍入,一般 1e-5 左右)
9. 动手作业
- 给
Value加exp、log方法,并推导它们的_backward。(提示:d(e^x)/dx = e^x,前向已算出的out.data可直接复用) - 用数值梯度对拍验证第 1 题和整个 MLP 的梯度(构造 20 个随机输入,最大相对误差应 < 1e-6 量级)。
- 把玩具任务换成 XOR 和”同心圆环”( 或 为正类),观察不同宽度的网络谁学得动——体会”容量”。
- 挑战题:把引擎升级成支持向量化的版本(参考 Karpathy 后续的
micrograd→ tinygrad 思路),为卷1手写 attention 做准备。
10. 延伸资源
- Karpathy《The spelled-out intro to neural networks and backpropagation》(YouTube/B站)——与本章一一对应
- micrograd 官方 repo(约 100 行)——读完本章后对照
- 《Neural Networks: Zero to Hero》系列 playlist——通往卷2 的 GPT 章节
0.4 训练工程常识:混合精度、断点续训、调试与监控
本章目标:把”能跑起来”和”跑得专业”之间的差距补上。这些是 AI 代码助手最容易漏掉、而实验失败时最烧时间的部分。学完标准:你的训练脚本具备断点续训、梯度裁剪、EMA、完整日志四件套,并且知道”训练出问题时的标准排查顺序”。
1. 混合精度(AMP):不只是”换个 dtype”
原理拆解:训练时前向和反向用低精度(bf16/fp16)加速,但主权重和优化器状态保持 fp32:
- 前向在
autocast里:框架自动把 matmul/conv 换成低精度,而 softmax、log、norm 统计等对精度敏感的算子保持 fp32(框架替你做了,但自己手写 loss 时要注意:对 logits 求对数前先.float()是保命习惯); - fp32 主权重:梯度更新量可能小于低精度的最小可表示数,直接在 fp16 权重上累加会被”吞掉”,所以低精度只是”计算现场”,真身永远 fp32;
- GradScaler 只在 fp16 下需要:fp16 指数位只有 5 位,小梯度会下溢为 0,所以先放大 loss(乘个 2^16 级别的数),反向后再缩小。bf16 指数位与 fp32 相同,动态范围大,完全不需要 scaler——这就是现代 GPU 上 bf16 一统江湖的原因。
回报:速度约 2 倍、显存大头(激活)减半。纪律:所有训练默认开 AMP;报 NaN 时第一嫌疑人是精度/学习率。
2. 梯度裁剪:LLM 训练的保险丝
torch.nn.utils.clip_grad_norm_(model.parameters(), max_norm=1.0)
放在 backward() 之后、step() 之前:若全体梯度的 L2 范数超过阈值,按比例整体缩小。动机:训练中偶发 loss spike(坏数据、精度抖动),spike 往往伴随梯度爆炸,一步就把权重打飞。NLP/LLM 训练默认裁剪到 1.0;CV 分类任务可不加。日志里同时记录裁剪前的 grad norm——它的突变是最好的异常报警器。
3. EMA:训练一份,评测另一份
指数滑动平均:维护权重影子副本 ( 常取 0.999)。理论依据:SGD 最终解附近来回震荡,EMA 是”震荡轨迹的平均”,落在更平坦的盆里,评测/部署普遍好零点几个点。LLM 和扩散模型训练标配(checkpoint 里经常同时存 raw 和 ema 两份权重)。实现可以直接用 torch.optim.swa_utils.AveragedModel,或几十行手写。
4. 断点续训(长训练的命根子)
只存 model.state_dict() 是新手做法。完整的 checkpoint 至少包含五样东西——否则中断后训练无法严格复原:
ckpt = {
"model": model.state_dict(),
"opt": opt.state_dict(), # AdamW 的动量状态丢了 = 训练"失忆"
"sched": sched.state_dict(), # 学习率进度
"epoch": epoch,
"rng": torch.get_rng_state(), # 随机状态(数据增强、dropout)
}
torch.save(ckpt, f"ckpt_ep{epoch}.pth")
# 恢复
model.load_state_dict(ckpt["model"]); opt.load_state_dict(ckpt["opt"])
sched.load_state_dict(ckpt["sched"])
for ep in range(ckpt["epoch"] + 1, total): ... # 从断点继续
工程惯例:定期存(每 N epoch)+ 只留最近 2 份 + 单独留最优 1 份,硬盘会被写爆的。LoRA 微调时额外注意:get_peft_model 后的模型要存 peft 格式,别直接存完整 state_dict(10GB 白送给硬盘)。
5. 可复现性三件套
- 全链路 seed:
random、numpy、torch、torch.cuda各设一次(封装成set_seed(s)函数); - 记录配置:git commit hash + 完整超参 dump 成 json/yaml 随 checkpoint 一起存——三个月后你会感谢自己;
- 接受不完全复现:cuDNN 非确定性算子(
torch.backends.cudnn.deterministic=True可关掉但速度损失大)。原则:复现 seed 内逐位一致不追求,追求同配置下结果稳定(多次运行指标方差小于效应量)。
6. 监控清单:训练时到底看什么
用 wandb(或 tensorboard)记录,缺一不可:
| 量 | 看什么 | 异常信号 |
|---|---|---|
| loss(原始+平滑) | 总趋势 | spike → 查 lr/坏数据;平台 → 查容量/瓶颈 |
| grad norm | 稳定范围 | 骤升 → 爆炸前兆(clip 阈值报警);趋 0 → 死了 |
| lr | 当前值 | 和 schedule 对照,warmup 没生效是常见 bug |
| 显存占用 | 峰值 | 接近上限 → OOM 风险(卷7 详述) |
| 吞吐 samples/s | 稳定性 | 骤降 → DataLoader 瓶颈(num_workers、IO) |
训练远程挂着时的正确姿势:loss spike 报警(wandb alert)+ 每小时自动 checkpoint,而不是盯屏。
7. 调试的标准动作:单 batch 过拟合
任何新模型/新数据/新 loss,跑全量训练前先做这一步——DL 调试的第一定律:
x, y = next(iter(train_loader)) # 只取一个 batch
for i in range(200):
loss = train_step(model, x, y) # 反复喂同一个 batch
print(loss) # 必须趋近 0
- loss 降不到接近 0 → 代码有 bug(标签错位、loss 写错、数据没对齐、梯度断了),不是模型能力问题。先修代码再谈调参;
- 能过拟合单 batch 但全量数据学不动 → 数据量/容量/增强过度的问题,方向是调参而非 debug。
配套两招:① 训练前可视化 8 个样本及其标签(眼睛看,30 秒抓住标签错位);② 先用最小模型 + 5% 数据跑通全流程(含评估和 checkpoint),再放大。顺序错了就是”训了 8 小时才发现标签错位”的悲剧。
8. 训练时长估算(租卡前必做)
例:LoRA 微调 7B,1 万条样本、3 epoch、batch 4、4090 实测约 0.5 samples/s → 10000×3/(4×0.5×3600) ≈ 4.2 小时 ≈ 10 元。下单前先跑 50 step 实测吞吐再乘,不要拍脑袋。
9. 自测题
- AMP 里什么是 fp32、什么是 bf16?为什么主权重必须 fp32?(激活与计算用 bf16;权重/优化器状态 fp32;低精度累加小更新会被吞)
- bf16 为什么不需要 GradScaler?(指数位 8 位同 fp32,动态范围大,小梯度不下溢)
- GradScaler 只在哪一步起作用?(backward 前 scale loss,step 前 unscale 梯度)
- 断点续训只存模型权重会怎样?(优化器动量清零、lr 进度重置、随机流错位——训练”失忆”且结果不可比)
- 单 batch 过拟合降不到 0,说明什么?(代码有 bug,按标签→loss→数据对齐→梯度链顺序排查)
- grad norm 趋近 0 且 loss 不降,两种可能?(学习率太小/梯度断了(detach 误用);或模型输出饱和)
- 吞吐骤降但 GPU 利用率低,先查什么?(数据加载:num_workers、磁盘 IO、pin_memory)
10. 动手作业(把 0.2 的脚本升级为”专业版”)
给 CIFAR 脚本加装四件套,每件独立 commit:
set_seed函数 + 配置 dump 成 json;- 完整 checkpoint(第 4 节五要素)+ 断点续训自测(kill 掉重启,loss 曲线应无缝衔接);
clip_grad_norm_+ wandb 记录 grad norm;- 单 batch 过拟合测试脚本
debug_overfit.py,以及一个故意注入标签错误的版本,观察它如何暴露问题。
11. 延伸资源
- Karpathy 博客《A Recipe for Training Neural Networks》——本章的加长原版,必读
- PyTorch 官方文档 AMP / autocast 页——API 细节查询
- wandb 官方 quickstart——10 分钟接入
0.5 Git / Linux / 远程开发生存包
本章目标:把”租了卡连不上、跑了实验找不到、改了代码乱了版”这三类新手事故一次性免疫——Git 工作流、Linux 命令生存集、远程开发环境三件套。学完标准:能独立在 AutoDL 上开机 → 拉代码 → 后台训练 → 断线恢复 → 取回结果。
1. Git:五个动作 + 一条铁律
日常 95% 的场景只需要:
git clone <url> # 取
git checkout -b feat/xxx # 开分支(实验与主线隔离)
git add -p && git commit -m "..." # 小步提交(-p 逐块审,防误提交大文件)
git push origin feat/xxx # 推
git log --oneline / git diff # 查
铁律:数据、权重、大文件不进 Git(.gitignore 里写死 data/ checkpoints/ *.pth *.gguf)——Git 是管代码的,二进制让它的一半历史都会爆。大文件的正确归宿:HuggingFace/ModelScope(模型)、网盘/对象存储(数据)、wandb(实验记录)。
与实验管理的接线(0.4 §5):每次实验记录 git commit hash——三个月后”这个结果对应哪版代码”永远有答案。
2. Linux 生存二十条(租卡环境的全部日常)
# 看:系统在干什么
nvidia-smi # GPU 占用(watch -n1 nvidia-smi 持续看)
htop # CPU/内存;df -h 磁盘;free -h 内存
# 找:文件与文本
find . -name "*.pth" # 按名找;du -sh * 看各目录体积(磁盘爆前的第一动作)
grep -rn "OOM" logs/ # 文本内搜(-r 递归 -n 行号)
# 管:进程
ps aux | grep python # 找进程;kill -9 <pid> 清僵尸(7.1 的第一步)
# 传:本地 ↔ 服务器
scp local.zip user@host:/root/ # 上传;反向即下载
# 解压/环境
tar -xzf file.tar.gz ; unzip file.zip
强制纪律:长训练必须挂后台——SSH 断线 = 前台进程死光 = 白训一夜(新手最痛的一课):
tmux new -s train # 新建会话,在其中跑 python train.py
# Ctrl+B 再按 D 脱离(进程继续);tmux attach -t train 随时回来
tmux ls # 查看所有会话
tmux/screen 二选一学会即可,这 30 分钟的学习换来你所有长训练的安全。
3. 远程开发三件套(按舒适度递增)
- SSH 直连:
ssh -p <端口> root@<主机>(AutoDL 会给完整命令);密钥登录(ssh-keygen+ 上传公钥)免密码; - VS Code Remote-SSH(推荐):本地 VS Code 装插件 → 连远程 → 像本地一样编辑远程文件、开远程终端、断点调试——本地写码的舒适 + 远程算力的实惠一次拿到;
- JupyterLab(平台自带):交互探索/画图方便,长训练仍走 tmux。
租卡流程模板(AutoDL 为例):开机 → 进 ~/autodl-tmp(数据盘,不扣费空间大)→ 克隆代码 → 下数据(huggingface-cli download 或平台网盘)→ 装环境(优先用平台的镜像/pip install -r requirements.txt)→ 先跑 50 step 冒烟(0.4 §8 的算力估算)→ tmux 里挂长训练 → 关机前把 checkpoint 拷回数据盘/下载。磁盘会满、进程会残留、接口会记错端口——第 2 节的命令就是为这些准备的。
4. 自测题
- Git 铁律是什么?大文件的三个正确归宿?(数据权重不进库;HF/网盘/wandb)
- 为什么前台跑长训练是事故?(SSH 断=进程死;tmux 会话独立于连接)
- tmux 脱离和杀掉的区别?(detach 保留进程 / kill 终止)
- 磁盘告急的第一个动作?(
du -sh *定位大头 + 清 checkpoint/缓存) - 远程开发推荐哪套?它解决了什么?(VS Code Remote——本地体验+远程算力)
- 租卡流程里”冒烟”指什么?为什么必做?(50 step 实测吞吐与显存——估算租期与预算,防”跑了一天才发现配置错”)
5. 动手作业(今天就能练,全部免费)
- 给你的笔记/代码 repo 建正式 Git 仓库:写好
.gitignore,完成”开分支→提交→合并”一轮; - 本机装 tmux(Windows 用 WSL 或 Git Bash 的 screen),体验 detach/attach 三次;
- 试跑 VS Code Remote-SSH:连任意一台你能访问的机器(或本地 WSL);
- 挑战:在 Kaggle/魔搭的免费环境里完成”clone 你自己的 repo → 跑通 CIFAR 5 epoch → 把日志和权重取回本地”的完整闭环——这个闭环跑通,你就有了全世界的算力。
6. 延伸资源
- 《Pro Git》前 2、3 章——免费官方书,够用终身
- The Missing Semester(MIT)——Shell/Git/工具课,与本章互补的第一名
- AutoDL 帮助文档——平台细节(端口/网盘/镜像)
1.1 从 CNN 到 ResNet:卷积时代的遗产
本章目标:用最小的篇幅吃透卷积神经网络——不是为了拥抱传统,而是因为:① 视觉 Transformer 至今仍在用卷积做 patch 化和下采样;② 小数据、小模型、边缘部署场景 CNN 仍是首选;③ CNN 时代沉淀的训练技术(数据增强、初始化、残差、蒸馏)全部延续到了大模型时代。学完标准:能手写 ResNet-18 在 CIFAR-10 上跑到 93%+,并能讲清”为什么残差连接有效”。
1. 卷积的四种视角(核心中的核心)
一维卷积你已熟悉(0.3 章)。二维图像卷积 有四种等价的理解,调试和阅读论文时来回切换:
- 模板匹配:卷积核是一组可学习的权重模板,滑动扫描图像找模式。第一层学到的常是边缘/色块检测器(Gabor 形状),这是数据自己学出来的,不是设计出来的。
- 感受野:输出某一点”看得见”输入的多大范围。堆叠规律:每叠一层 3×3 卷积,感受野 +2——两层 3×3 = 5×5 的感受野,但参数只有 2×9=18 而不是 25,还多了一次非线性。小核堆叠优于大核,这条设计法则统治了 2014–2020。
- 参数共享:同一组核扫过全图 = “猫在左上角和右下角是同一种猫”的先验。这叫平移等变性。全连接层没有这个先验,所以需要更多数据——这个观点是理解”卷积 → Transformer”变迁的钥匙(见第 6 节)。
- 稀疏的矩阵乘法:卷积 = 权重共享的全连接层(用 im2col 展开后就是一次矩阵乘)。所以 GPU 对卷积优化得极好,卷积从不”慢”在数学上,而是”慢”在内存访问模式上。
实用公式(必背):输出尺寸 (输入 N、核 K、填充 P、步长 S)。参数量 (无 bias 时)。
2. 一个现代卷积块的标准结构
- Conv 不带 bias:因为 BN 里本来就有可学习的平移项,加 bias 纯属浪费参数;
- BN 在 0.3 章讲过:稳定各层输入分布;
- 1×1 卷积:跨通道的加权混合,用于降维/升维(bottleneck 结构里先降再升,省算力);
- 池化/步长卷积负责下采样:MaxPool 取局部最大(保显著特征),步长卷积让下采样本身可学习(现代默认)。
3. ResNet:深度的闸门被打开
2015 年之前,网络加深到 20+ 层反而变差——不是过拟合(训练误差也差),而是退化:深层网络难以优化。
残差连接把每个块改成学习”增量”:,其中 是普通卷积堆。
为什么有效(两层解释都要会):
- 梯度直通:反向传播时 ,那个”1”给梯度修了一条高速公路,100 层的梯度也不会层层衰减。消融实验:110 层网络去掉残差后训练误差降不下去,加上后正常——证明是优化问题而非容量问题。
- 学习目标的重塑:网络学的是”在恒等映射基础上改多少”。对多数层来说最优解接近恒等,把恒等设为默认值,让”什么都不做”变得容易——这是所有现代架构(Transformer 残差流、LoRA 的 )共享的哲学:学习增量,而不是从头学。
代码(BasicBlock,背下来,作业要用):
import torch, torch.nn as nn
class BasicBlock(nn.Module):
def __init__(self, cin, cout, stride=1):
super().__init__()
self.conv1 = nn.Conv2d(cin, cout, 3, stride, 1, bias=False)
self.bn1 = nn.BatchNorm2d(cout)
self.conv2 = nn.Conv2d(cout, cout, 3, 1, 1, bias=False)
self.bn2 = nn.BatchNorm2d(cout)
self.shortcut = nn.Sequential() # 默认恒等
if stride != 1 or cin != cout: # 形状不一致时用 1×1 投影
self.shortcut = nn.Sequential(
nn.Conv2d(cin, cout, 1, stride, bias=False),
nn.BatchNorm2d(cout))
def forward(self, x):
out = torch.relu(self.bn1(self.conv1(x)))
out = self.bn2(self.conv2(out))
return torch.relu(out + self.shortcut(x)) # y = x + F(x)
ResNet-18 = 一个 7×7 stem + 4 个 stage(每 stage 2 个 BasicBlock,通道 64→128→256→512)+ 全局平均池化 + 线性头。CIFAR-10 上把 stem 换成 3×3(图像小,7×7 太浪费)。
4. CNN 时代留给大模型时代的遗产
这些技术你会在所有后续章节反复遇到,现在建立索引:
| 技术 | 一句话 | 在大模型时代的下落 |
|---|---|---|
| 数据增强(翻转/裁剪/颜色抖动) | 免费扩数据防过拟合 | VLM 数据管线仍在用(随机裁剪、颜色扰动) |
| 标签平滑 | one-hot 里的 0.9/0.1,防过度自信 | LLM SFT 常用 |
| Mixup/CutMix | 图像线性混合、标签同步混合 | 视觉预训练数据增强标配 |
| 知识蒸馏 | 大模型教小模型(KL + 温度) | 推理侧核心技术,卷5.8 |
| 权重衰减/早停/EMA | 0.4 章已讲 | 全部沿用 |
| Pre-training → Fine-tuning 范式 | ImageNet 预训练 + 下游微调 | 被”自监督预训练 + 指令微调”继承,范式本身没变 |
5. 检测与分割:知道即可
- 检测:YOLO 系(快,工业部署多)、DETR 系(transformer 化);分割:FCN → U-Net(医学影像至今主流)→ Mask R-CNN → SAM。你不需要复现它们,只需要:知道任务定义、知道 U-Net 的编码器-解码器 + 跳跃连接结构(扩散模型的 U-Net 就是它)、知道 SAM 是”可提示分割基础模型”(1.7 章)。
6. 卷积让位给了什么?——归纳偏置与数据规模的交易
卷积内置了两个先验:局部性(近邻像素相关)+ 平移等变。先验强 = 小数据学好,大数据下变成天花板(没法学全局关系,感受野增长太慢)。ViT 的赌注是:把图像切成 16×16 patch 当作 token 序列,用几乎无视觉先验的 Transformer,让数据补足先验——数据规模到亿级后反超 CNN,且天然兼容文本 token(这条兼容性直接通向多模态,卷3 的主角)。
记住这条主线:CV 的十年 = 先验逐渐变少、数据规模逐渐变大、架构逐渐统一到 Transformer。这不是”CNN 错了”,而是不同数据规模下的最优权衡。小数据(医学影像标注贵)场景 CNN/混合架构至今能打。
7. 自测题
- 输入 224×224,3×3 卷积、stride=2、padding=1,输出多大?(112×112,套公式)
- 为什么现代卷积块里 Conv 不带 bias?(BN 的平移参数替代了它)
- 两层 3×3 卷积的感受野等于一层多大卷积?参数量对比?(5×5;18 vs 25,还多一次非线性)
- 残差连接的梯度公式里”1”意味着什么?(梯度至少有一部分不衰减地直通,缓解深层退化)
- “学习增量而非从头学”这个哲学还出现在哪两处?(Transformer 残差流;LoRA 的低秩增量)
- ViT 为什么在大数据下反超 CNN?(弱先验架构容量上限高,数据规模补足先验)
- U-Net 的跳跃连接解决什么问题?(下采样丢失的空间细节通过 skip 直接传给解码器;扩散模型沿用此结构)
8. 动手作业
- 用第 3 节的 BasicBlock 搭 CIFAR 版 ResNet-18(stem 用 3×3,无 maxpool),在 0.2 章训练脚本里替换
Net,目标 ≥93%(配合 TrivialAugment 增强)。 - 训练完后可视化第一层卷积核(
model.features[0].weight归一化后plt.imshow)——亲眼看看”学出来的边缘检测器”。 - 挑战:故意删掉所有 shortcut 再训 20 epoch,对比训练曲线,亲手复现”退化”现象。
- 把你的训练记录写成 README 传 GitHub——作品集第一块砖。
9. 延伸资源
- CS231n 课程笔记(卷积网络部分)——卷积直觉的第一名
- 李沐《论文精读》ResNet 一期 + 原论文 Deep Residual Learning(2015)
- CS231n 2024 新版公开课——后半程直接过渡到 Transformer
1.2 注意力机制:从加权检索到万物的基础操作
本章目标:把”注意力”从玄学变成一个你闭眼能写的函数。它是整个大模型时代唯一的计算原语——CV 里它取代了卷积,LLM 里它就是全部,多模态里它负责图文对齐。学完标准:能手写带 causal mask 的多头注意力并与 PyTorch 内置实现对拍,能解释 1/√d 的来历。
1. 为什么需要注意力:RNN 的两大死穴
Transformer 之前序列建模靠 RNN/LSTM:逐 token 读取,用隐状态”记忆”历史。两个致命问题:
- 无法并行:第 t 步依赖第 t−1 步,GPU 上万个核心干等着看一个序列爬行;
- 长程依赖衰减:信息要经过 O(N) 次状态更新才能传到远处,距离一长就被冲淡(梯度消失的序列版)。
注意力的解法釜底抽薪:不递归传递信息,让任意位置一步直达任意位置——距离消失,同时整个序列的计算可以一次矩阵乘完成。2017 年《Attention Is All You Need》标题的狂妄就在于此。
2. 注意力的通用形式:一次可微分的”查字典”
想象查字典:你有一个查询 Q(想找什么),字典里每个词条有键 K(索引)和值 V(内容)。硬字典是 argmax 检索(不可导),注意力做的是软检索:
三步拆解(每步都有几何直觉):
- 打分: 算出每个 query 和每个 key 的内积——内积 = 对齐程度 = 相关性(0.1 章 §2.1);
- 归一化:softmax 把分数变成总和为 1 的权重分布——“把 100% 注意力分配给各位置”;
- 加权求和:输出 = 各位置的 value 按注意力权重混合。
一句话本质:注意力是按相关性加权的加权平均,而相关性用内积度量,权重用 softmax 归一,全部可导,因此可以端到端学习。 图像块之间做它 = ViT;图像与文本之间做它 = CLIP 式对齐;序列自己内部做它 = GPT。万物皆注意力。
3. 为什么除以 √d_k(面试与理解双高频)
假设 q 和 k 的各分量独立、零均值、方差 1,则内积 的方差是 (方差相加),标准差 。d=128 时,打分普遍在 ±11 上下波动——softmax 在这么大的输入下会饱和:最大项拿到几乎全部概率,其余趋近 0,梯度消失,且分布对输入噪声极其敏感。
除以 把打分的方差拉回 1,softmax 保持”清醒”。这是”方差控制”思想——和初始化(0.3 章 §5)、RMSNorm 是同一个思想在不同位置的应用:让每层输出的数值尺度保持稳定。
4. Self-Attention 与 Multi-Head
- Self-attention:Q、K、V 全部来自同一个序列(各自过三个线性投影 )。每个位置同时是查询者、被查者和内容提供者——序列内的信息交换。
- Cross-attention:Q 来自 A 序列,K/V 来自 B 序列。多模态的桥(LLaVA 里文本 query 查图像特征)、翻译里译文查原文,都是它。
- Multi-Head:把 d 维投影拆成 h 个 64 维子空间,各自独立做注意力再拼接。动机:一组 QKV 只能表达一种”关注模式”,多头 = 多个视角并行(语法一=head1,指代一=head2……)。与 CNN 的多通道异曲同工:并行多组特征提取器,各学各的。
5. Causal Mask:让 GPT 不会”作弊”
语言模型预测第 t 个 token 时只能看前文。实现:把 矩阵的上三角(未来位置)在 softmax 前填 ,softmax 后权重为 0:
mask = torch.tril(torch.ones(N, N, dtype=torch.bool)) # 下三角为 True
scores = scores.masked_fill(~mask, float("-inf"))
记住这个机制的名字:解码器里的自回归 = causal mask + 逐位预测。卷3 LLaVA 复现、卷4 自回归生成模型(Janus 路线),全靠它。
6. 手写实现 + 对拍(本章作业的骨架)
import torch, torch.nn as nn, torch.nn.functional as F, math
def attention(q, k, v, mask=None):
"""q,k,v: (B, H, N, D) mask: (N, N) bool, True=可见"""
d = q.size(-1)
scores = q @ k.transpose(-2, -1) / math.sqrt(d) # (B,H,N,N)
if mask is not None:
scores = scores.masked_fill(~mask, float("-inf"))
return F.softmax(scores, dim=-1) @ v # (B,H,N,D)
class MultiHeadAttention(nn.Module):
def __init__(self, d_model, n_head):
super().__init__()
assert d_model % n_head == 0
self.h, self.dh = n_head, d_model // n_head
self.qkv = nn.Linear(d_model, 3 * d_model, bias=False) # 一次投影三份,省两次 GEMM
self.proj = nn.Linear(d_model, d_model, bias=False) # 输出融合投影
def forward(self, x, mask=None):
B, N, D = x.shape
q, k, v = self.qkv(x).split(D, dim=2) # 各 (B,N,D)
q, k, v = (t.view(B, N, self.h, self.dh).transpose(1, 2) for t in (q, k, v)) # (B,H,N,dh)
out = attention(q, k, v, mask) # (B,H,N,dh)
out = out.transpose(1, 2).contiguous().view(B, N, D)
return self.proj(out)
# 对拍验证
x = torch.randn(2, 16, 128)
mha = MultiHeadAttention(128, 8); mha.eval()
mine = mha(x)
q, k, v = mha.qkv(x).split(128, dim=2)
ref = F.scaled_dot_product_attention(
q.view(2,16,8,16).transpose(1,2), k.view(2,16,8,16).transpose(1,2), v.view(2,16,8,16).transpose(1,2))
ref = ref.transpose(1,2).reshape(2,16,128)
print((mha.proj(ref) - mine).abs().max()) # 应 < 1e-6
工程常识:真实训练用 F.scaled_dot_product_attention——它自动分派到 FlashAttention 内核。FlashAttention 你不需要实现,只需记住它的思想:不做优化数学,优化显存读写(避免把巨大的 N×N 注意力矩阵写进显存再读出来,用分块重算换取 10 倍级速度)——这是”系统工作”在大模型里值钱程度的最好例子。
7. 代价与对比
- 复杂度 :注意力矩阵 N×N 是显存和时间的大头。长上下文、高分辨率图像(patch 数多)、视频(帧数爆炸)的成本都从这里来——卷3/4 里所有”长上下文""多帧”问题,根源都是这个平方项。
- 与卷积的对比表(理解架构选择的地图):
| 卷积 | Self-Attention | |
|---|---|---|
| 感受野 | 局部,逐层扩大 | 全局,一步到位 |
| 参数 | 共享,先验强 | 投影矩阵,先验弱 |
| 数据效率 | 小数据占优 | 大数据占优 |
| 位置信息 | 结构自带 | 必须额外注入(→1.3 位置编码) |
| 多模态亲和 | 弱(模态间无天然接口) | 强(都是 token 序列) |
8. 自测题
- 注意力的三步是什么?各自的作用?(打分/归一化/加权求和)
- 1/√d 的方差推导为什么假设零均值独立?(中心极限式的和:分量方差相加,d 项 → 方差 d)
- Self 和 Cross attention 的区别一句话?(Q 和 K/V 是否同源)
- 为什么多头而不是一个大的头?(多组子空间并行学不同关注模式;总计算量不变)
- causal mask 填 −∞ 而不是 0,为什么?(softmax 后 0 权重需要 −∞ 分数;填 0 会产生非零注意力泄漏未来信息)
- 注意力的平方复杂度在哪一步产生?它如何影响视频生成的帧数上限?( 的 N×N 矩阵;帧数↑→N↑→平方爆炸)
- FlashAttention 优化的是什么资源?(显存读写 IO,不是浮点计算)
9. 动手作业
- 跑通第 6 节对拍代码;然后给
MultiHeadAttention加 causal mask 支持,用is_causal=True的内置实现再对拍。 - 可视化注意力:随机初始化 + 训练一个 2 层小模型在玩具序列任务上(如反转数字序列),用 matplotlib 画
softmax(scores)热力图,观察注意力”看见了什么”。 - 把第 6 节的 MHA 包进 Transformer block(残差 + LayerNorm + MLP),就是 1.3 章的开头——提前搭好骨架。
- 挑战:读 FlashAttention 论文第 1-2 节,用三句话讲清”分块 + 重算”为什么省显存。
图解 · 一次注意力的完整数据流
flowchart TB
X["输入 x (B×N×D)"] --> QKV["单个 Linear 投影出 3D 维"]
QKV --> S["拆成 Q / K / V (B×H×N×d_h)"]
S --> SC["scores = QKᵀ/√d_h → (B×H×N×N)"]
SC --> M["causal mask:未来位置填 −∞"]
M --> SM["softmax(每行归一成权重)"]
SM --> AV["加权求和 scores @ V"]
AV --> CO["concat 所有头 (B×N×D)"]
CO --> PJ["输出投影 W_O"]平方成本就藏在 scores 那个 N×N 矩阵里——N 翻倍它变四倍:这是 2.3 的 KV cache 账、2.8 的 prefill 瓶颈、3.3 的 token 压缩,全部问题的同一源头。
案例:两个 token 的迷你注意力(全手算)
设 D=2、单头,序列 [“the”, “cat”],投影后 ,,V 取值同 K。
位置 1(有 causal mask)只看自己 → 权重 ; 位置 2 看两个:, → softmax 各 0.5 → 输出 。
你刚刚手动执行了 GPT 的一层。四句话总结注意力:mask 决定能看谁,内积决定多想看,softmax 归一成百分比,加权求和取材料。
10. 延伸资源
- 李沐《论文精读》Transformer 一期——逐段精读 Attention Is All You Need
- Jay Alammar《The Illustrated Transformer》——图解第一名
- Karpathy《Let’s build GPT: from scratch》——本笔记 1.3/2.3 章的实拍版
1.3 Transformer 逐层拆解:从 Block 到小 GPT
本章目标:把 1.2 的注意力装进完整的 Transformer,逐个组件搞清”它解决什么问题、现代版本是什么”,最后手写一个能跑的小 GPT。这一章是卷2(LLM 内功)的地基——学完它,nanoGPT 对你只剩工程细节。前置:1.2(注意力)、0.3(RMSNorm)。
1. 宏观地图:三种架构,为什么 decoder-only 赢了
| 架构 | 代表 | 注意力 | 擅长 | 命运 |
|---|---|---|---|---|
| Encoder-only | BERT | 双向 | 理解类任务(分类/检索) | 沦为嵌入模型 |
| Decoder-only | GPT | 因果 mask | 生成 + 通用任务 | 大模型时代的主宰 |
| Encoder-decoder | T5 | 双向+交叉 | 翻译等 seq2seq | 特化场景 |
decoder-only 胜出的原因(面试高频):训练目标最简单(每个位置都预测下一个 token,1 个 token 的数据产出 1 个监督信号)、生成和理解是同一件事(都是”给定前文续写”)、架构最简(没有 encoder-decoder 的交互设计)、天然支持 in-context learning。BERT 式”完形填空”目标学到的表示很好,但生成弱、扩展性叙事输给了 GPT。
2. Block 结构:Pre-Norm 为什么取代了 Post-Norm
原版 Transformer(Post-Norm):
现代(Pre-Norm,GPT-2 之后所有主流模型):
区别在 Norm 包住的是子层输入还是子层输出。Pre-Norm 的残差主干上没有任何变换,梯度从顶层直通底层不经过任何 LN/非线性——深层网络(百层)训练稳定的关键。代价是表达力略降,所以现代模型在最后加一个 final norm(你读 Qwen/LLaMA 代码时看到的 ln_f 就是它)。0.3 章讲过 Norm 本身,现在你有了它为什么”在这里”的完整答案。
3. 逐组件拆解
3.1 输入端:token embedding + 位置信息
注意力本身是置换等变的——打乱输入顺序,输出跟着同样打乱,“位置”完全丢失。序列任务必须显式注入位置:
- 正弦编码(原版):固定三角函数,相对位置可线性表达;
- 可学习绝对位置(GPT-2):一张
nn.Embedding(n_ctx, d)表,简单有效,但不能外推到训练长度之外; - RoPE(旋转位置编码):现代主流(LLaMA/Qwen/GLM 全家)。直觉版:把 q、k 的维度两两配对,在 attention 内积前按位置旋转一个角度——旋转角随位置线性增长,于是 只依赖相对距离 ,天然相对位置、天然可外推(配合 NTK/YaRN 等缩放技巧做长上下文)。不需要会推导,需要会一句话讲清思想和好处。
3.2 注意力层
1.2 章已手写。现代补充细节:qkv 用一个矩阵一次投影(省两次 GEMM);对 q、k 做 norm(QK-Norm,稳定大模型训练的新趋势,Qwen3 等在用)。
3.3 MLP:不比注意力次要
原版:Linear(d → 4d) → GELU → Linear(4d → d),占每层约 2/3 参数(见第 5 节的账)。现代升级为 SwiGLU:三个矩阵(gate/up/down),down(silu(gate(x)) * up(x))——门控让网络自己决定”哪些特征放行”。LLaMA/Qwen 全在用;为保持参数量与 4d 版本对齐,中间维度取约 8d/3。注意力的作用是”位置间搬运信息”,MLP 的作用是”位置内加工信息”——可解释性研究(残差流视角)的基本分工认知。
3.4 残差流视角(建立这个心智模型)
把 Block 看成:残差主干是一条”信息高速公路”,注意力层和 MLP 层以加法方式向主干读写信息。训练后期大量层接近恒等映射。这个视角来自可解释性研究,但工程上同样有用:调 bug 时想”信息怎么流的”比想”第几层算错了”更有效。
4. 手写小 GPT(完整可运行)
import torch, torch.nn as nn, torch.nn.functional as F, math
class CausalSelfAttention(nn.Module):
def __init__(self, d, h, n_ctx):
super().__init__()
self.h, self.dh = h, d // h
self.qkv = nn.Linear(d, 3 * d, bias=False)
self.proj = nn.Linear(d, d, bias=False)
mask = torch.tril(torch.ones(n_ctx, n_ctx)).view(1, 1, n_ctx, n_ctx)
self.register_buffer("mask", mask) # 随模型保存/迁移,不参与训练
def forward(self, x):
B, N, D = x.shape
q, k, v = self.qkv(x).split(D, dim=2)
q, k, v = (t.view(B, N, self.h, self.dh).transpose(1, 2) for t in (q, k, v))
att = (q @ k.transpose(-2, -1)) / math.sqrt(self.dh)
att = att.masked_fill(self.mask[:, :, :N, :N] == 0, float("-inf"))
y = F.softmax(att, dim=-1) @ v
y = y.transpose(1, 2).contiguous().view(B, N, D)
return self.proj(y)
class Block(nn.Module):
def __init__(self, d, h, n_ctx):
super().__init__()
self.ln1, self.ln2 = nn.LayerNorm(d), nn.LayerNorm(d)
self.attn = CausalSelfAttention(d, h, n_ctx)
self.mlp = nn.Sequential(nn.Linear(d, 4 * d), nn.GELU(), nn.Linear(4 * d, d))
def forward(self, x): # Pre-Norm
x = x + self.attn(self.ln1(x))
x = x + self.mlp(self.ln2(x))
return x
class TinyGPT(nn.Module):
def __init__(self, vocab, d=256, h=4, L=4, n_ctx=128):
super().__init__()
self.tok = nn.Embedding(vocab, d)
self.pos = nn.Embedding(n_ctx, d)
self.blocks = nn.ModuleList([Block(d, h, n_ctx) for _ in range(L)])
self.ln_f = nn.LayerNorm(d)
self.head = nn.Linear(d, vocab, bias=False) # 可与 tok.weight 绑定(权重 tying)
self.n_ctx = n_ctx
def forward(self, idx):
x = self.tok(idx) + self.pos(torch.arange(idx.size(1), device=idx.device))
for blk in self.blocks: x = blk(x)
return self.head(self.ln_f(x))
@torch.no_grad()
def generate(model, idx, n_new=60, temperature=1.0, top_k=20):
for _ in range(n_new):
logits = model(idx[:, -model.n_ctx:])[:, -1] / temperature # 只看最近 n_ctx
if top_k:
kth = logits.topk(top_k, dim=-1).values[..., -1, None]
logits = logits.masked_fill(logits < kth, float("-inf"))
probs = F.softmax(logits, dim=-1)
idx = torch.cat([idx, torch.multinomial(probs, 1)], dim=1)
return idx
训练循环就是 0.2 章那套:logits = model(x); loss = F.cross_entropy(logits[:, :-1].reshape(-1, V), y[:, 1:].reshape(-1))——注意输入右移一位(预测下一个 token)。加上 0.4 章的四件套,你就有了一个完整的 nanoGPT。
5. 参数量的账(必须会算)
每个 Block:注意力 (QKV 投影 + 输出投影 )+ MLP = 。
验算 GPT-2 small: → ;词表嵌入 ;位置 。合计 ≈124M,和论文对上了。会算这笔账,你就能自己估算任何模型的显存(0.2 章 §7)和 LoRA 目标模块的选择(LoRA 常挂在哪些 上)。
6. 自测题
- Pre-Norm 相比 Post-Norm 的核心优势?(残差主干无变换,梯度直通,百层可训;final norm 补表达力)
- 为什么必须有位置编码?RoPE 一句话思想?(注意力置换等变;按位置旋转 q/k 使内积只依赖相对距离)
- MLP 占每层参数的比例?它和注意力分工是什么?(约 2/3;位置内加工 vs 位置间搬运)
- decoder-only 赢在哪些点?(目标简单数据利用率高、生成理解统一、架构简洁、支持 in-context learning)
- 权重 tying 是什么,省多少?(embedding 和输出投影共享,省 ,小词表模型占比可观)
- 采样时 temperature=0.1 和 5 分别是什么行为?(接近贪心;接近均匀随机、胡言乱语)
- 为什么 generate 时要裁剪 idx 到最近 n_ctx?(位置编码表长度有限——绝对位置的硬伤,RoPE 缓解此问题)
7. 动手作业
- 跑通 TinyGPT:用莎士比亚字符级数据(Karpathy
input.txt,词表 65)训到 loss ≈ 1.5,generate出一段”伪莎翁”。对照 Karpathy《Let’s build GPT》逐行验证你的实现。 - 算一笔账:你的 TinyGPT(d=256, L=4)参数量是多少?用
sum(p.numel())验证。 - 把 LayerNorm 换成 RMSNorm、把 top-k 换成 top-p,各写一版。
- 挑战:加 dropout 和权重衰减后把 L 加到 6,观察过拟合边界——体会”小数据喂不大模型”。
案例 · 手算:TinyGPT 一次前向的形状流
案例:张量形状从头流到尾(B=4, N=128, D=256, H=4, 词表=65)
- 输入 idx:(4, 128) 整数;
- tok+pos embedding:(4, 128, 256);
- 每个 Block 内:q/k/v 各 (4, 4, 128, 64);注意力分数 (4, 4, 128, 128)——这 26 万个数就是”平方成本”的本体;
- 加权求和回 (4, 128, 256),MLP 内部先膨胀到 (4, 128, 1024) 再压回;
- 最终 head:(4, 128, 65) logits → 对 127 个位置算 next-token loss。
参数量(§5 公式):每 Block 12×256²=786K,4 个 Block=3.15M;加词表嵌入 65×256≈17K——
sum(p.numel())应约 3.2M。形状对不上 = 90% 的 reshape/transpose bug(0.2 §2.2 的三兄弟再查一遍)。
8. 延伸资源
- Karpathy《Let’s build GPT: from scratch, in code, spelled out》——与本章一一对应,必跟
- nanoGPT repo——工业级微缩版(DDP、配置系统、都在)
- Jay Alammar《The Illustrated GPT-2》——图解推理时 KV 的流动
1.4 ViT 与视觉 Transformer 谱系:图像成为 token
本章目标:理解”图像怎么变成 token 序列”——这是整个多模态大厦的第一块砖。学完标准:能讲清 ViT 的最简设计与它成立的前提,知道主流变体解决什么问题,明白”视觉 token 数量”为什么是多模态的核心矛盾(卷3 的伏笔)。
1. ViT:最简单的设计为什么成立
《An Image is Worth 16x16 Words》(2020) 的做法简单到失礼:
- 把 224×224 图像切成 196 个 16×16 patch;
- 每个 patch 展平(16×16×3=768 维),过一个线性层 → 768 维 token;
- 加 [CLS] token(汇总全局信息,作分类头输入)+ 位置编码;
- 喂给标准 Transformer encoder(和 NLP 一模一样),CLS 输出接分类头。
工程等价性(必懂):切 patch + 线性投影 = 一个 stride=16、kernel=16 的卷积:
self.patch_embed = nn.Conv2d(3, 768, kernel_size=16, stride=16) # (B,3,224,224) → (B,768,14,14)
# 再 flatten + transpose → (B, 196, 768),拼上 CLS token,加位置编码,进 Transformer
第一层卷积参数 = 16×16×3×768,就是 N 个”patch → token”的线性映射。所以 ViT 并没有抛弃卷积,只是把卷积压缩成了一次 token 化,之后全交给注意力。
成立的前提:1.1 章讲过,弱先验架构需要大数据。ViT 论文自己的实验梯度——ImageNet-1k(百万级)上 ViT 输给 ResNet;ImageNet-21k + JFT-300M(亿级)上反超。结论不是”ViT 更好”,而是”数据规模换架构先验”的交易曲线。小数据场景(医疗影像常见)ViT 未必赢——这正是 DeiT 和混合架构存在的原因。
2. 谱系速览:每个变体在解决什么
| 变体 | 解决的问题 | 关键设计 | 现状 |
|---|---|---|---|
| ViT | 证明可行 | 最简设计 | 一切的起点 |
| DeiT | ImageNet-1k 也能训好 ViT | 强增强 + 蒸馏 token | 数据增强哲学被全行业继承 |
| Swin | 检测/分割需要高分辨率 | 层级下采样 + 窗口注意力(窗口内算,跨窗口移位交互) | 检测分割时代主力,现被 ViTDet 等挑战 |
| ConvNeXt | 用现代配方让 CNN 回牌桌 | 大核、LayerNorm、GELU 等逐项改造 ResNet | 证明”训练配方”≈“架构” |
| BEiT / EVA | 视觉预训练 | 遮罩重建 / CLIP 蒸馏 | 思想汇入自监督(1.5) |
读谱系的正确姿势:不是记名字,而是看张力轴——局部先验 vs 全局交互、窗口稀疏 vs 全局平方复杂度、纯视觉 vs 图文联合。所有变体都在这几根轴上找位置。
3. 视觉 token 数量:多模态的核心矛盾(卷3 伏笔)
算一笔账:224² 分辨率 → 196 token,没问题。但:
- 文档/OCR 要看清小字:需要 1024+ 分辨率 → 数千 token;
- 检测要 800×1333 → 约 2700 token(patch16);
- 视频每帧 196 token,16 帧就是 3136 token;
- 而 LLM 的注意力对 token 数平方敏感(1.2 章的账)。
多模态模型设计的核心工程问题之一就是:视觉 token 塞多少、怎么压。你以后会遇到的每个设计——Qwen-VL 的 pixel shuffle 压缩、BLIP-2 的 Q-Former(32 个 query token 打包整图)、Qwen3-VL 的动态分辨率 patch 化——都是在回答同一道题。现在记住题目本身:分辨率↑ → token 爆炸 → 注意力平方爆炸。
4. 实操:用 timm 玩真模型
import timm, torch
model = timm.create_model("vit_base_patch16_224", pretrained=True)
model.eval()
print(model) # 逐行读:patch_embed / cls_token / pos_embed / blocks.0...11 / head
x = torch.randn(1, 3, 224, 224)
feats = model.forward_features(x) # (1, 197, 768):196 patch + 1 CLS
print(feats.shape)
要求自己能对着打印输出说出每个模块的角色(对照本章 §1 和 1.3)。再从 model.blocks[i].attn 里抓 attention 权重画热力图,看最后一层注意力聚焦在哪——通常围绕物体轮廓(1.5 章 DINO 会把这个现象做到极致)。
5. 视觉编码器在多模态里的位置(前瞻)
到 2026 年,几乎所有开源 VLM 的视觉塔都是 ViT 变体(CLIP ViT、SigLIP、InternViT、AIMv2……),差别在训练目标和数据。你将来做 VLM 微调时冻结/解冻的就是这个东西。现在建立”视觉塔 = 冻结的 ViT 特征提取器”的直觉,卷3 会反复用到。
6. 自测题
- 切 patch + linear 等价于什么卷积?(k=16, s=16;参数即投影矩阵)
- ViT 为什么需要 CLS token 或全局池化?(输出是 196 个 token,要一个汇聚全局的向量做分类)
- ViT 在 ImageNet-1k 上输给 ResNet 说明什么先验问题?(弱先验架构数据不足时不如强先验;平移等变/局部性在中小数据仍有价值)
- Swin 的窗口注意力在省什么?(N² 注意力 → 窗口内线性增长;代价是牺牲部分全局交互,用移位窗口补偿)
- 1024×1024 图像 patch16 是多少 token?对 VLM 意味着什么?(4096 个;不压缩的话 LLM 端注意力代价爆炸——token 压缩是多模态核心工程题)
- ConvNeXt 的结论对科研方法论有什么启示?(配方与架构同样重要——复现失败先怀疑训练配方,再怀疑思想)
7. 动手作业
- 手写
PatchEmbed(conv 实现 + CLS + 可学习位置编码),前向输出 (B, 197, 768),与 timm 的model.patch_embed对比参数量。 - 用 timm 加载 ViT,冻结全部参数,只把 head 换成 10 类,在 CIFAR-10 上微调(只训 head,lr 1e-3;再试解冻最后 2 个 block,lr 1e-5)——体会”预训练特征 + 轻量适配”的威力与冻结/解冻的取舍。
- 可视化第 0/6/11 层 block 的 CLS→patch 注意力图,对比”低层看纹理、高层看物体”。
- 挑战:把输入改成 384×384(timm 的
img_size参数或直接换vit_base_patch16_384),观察位置编码怎么变——引出”插值位置编码”这一经典工程 trick。
8. 延伸资源
- ViT 原论文 + 李沐《论文精读》ViT 一期——必读必看
- Swin / ConvNeXt 论文泛读(看图说话级别即可)
- timm repo(
pytorch-image-models)——视觉 backbone 的瑞士军刀,后面项目反复用
1.5 自监督三巨头:MAE、CLIP、DINO
本章目标:理解”没有标签,监督信号从哪来”——这是预训练范式的燃料学。三巨头对应三条路线:遮住重建(MAE)、图文对齐(CLIP)、自己教自己(DINO)。学完标准:能说清每种方法的信号构造方式和防坍塌机制,明白为什么 CLIP 成为多模态地基、DINO 成为机器人底座。CLIP 的实操放在 1.6。
1. 为什么需要自监督
监督学习的燃料是人工标注,两个天花板:标注贵(分割一个像素级标注几分钟)和标注偏(人标的分类体系 ≠ 模型需要的特征)。自监督(self-supervised learning)的思路:构造一个”答案就在数据里”的代理任务——遮住一部分让模型补全、把配对的图文拼起来、对同一张图做两次增强要求输出一致。预训练学到的通用特征再迁移到下游。这个”预训练 → 迁移”范式,就是后来 LLM”预训练 → 微调”的直系祖先。
2. MAE:遮住 75%,重建像素
《Masked Autoencoders Are Scalable Vision Learners》(2021),思路来自 BERT 的完形填空:
- 把图像切成 patch(16×16),随机遮住 75%;
- 编码器(ViT)只处理可见的 25%(196 → 49 个 token,计算量省 3 倍多);
- 轻量解码器拿”可见 token + 可学习的 mask token”去重建被遮 patch 的像素;
- loss 只在被遮位置算 MSE。
两个设计点是全文精华:
- 75% 这么高的遮罩率为什么行:自然图像冗余度极高(遮 15% 邻居一 interpolation 就补上了,学不到东西);75% 迫使模型利用全局语义推断(补全人脸必须懂人脸结构)。语言的信息密度高,BERT 只遮 15%——遮罩率跟着模态冗余度走,这个对比本身就是一道理解题;
- 非对称架构:重编码器 + 轻解码器。重建任务只是训练的”脚手架”,推理时解码器直接扔掉,只留编码器产特征。
遗产:MAE 证明了”生成式代理任务”在视觉成立,遮罩重建思想后来汇入多模态预训练和统一模型(卷3/4)。
3. 对比学习:CLIP 及其思想基础
在讲 CLIP 之前先给对比学习的最小内核(SimCLR/MoCo 一句话历史:同一张图两次增强互为正样本,batch 内其余为负样本,拉近正样本、推远负样本——难点在防坍塌)。
CLIP(Contrastive Language-Image Pre-training, 2021) 把”正样本”换成”配对的图文”:
- 数据:4 亿张互联网图文对(WIT-400M)——不标注,只利用”网页图片旁边通常有描述”这个天然结构;
- 模型:图像塔(ViT)+ 文本塔(Transformer),各自输出归一化嵌入;
- 目标(对称 InfoNCE):batch 内 N 对图文,对角线上的图文对相似度拉高,其余 N²−N 对推低:
(前半:每张图找它的文本;后半:每段文本找它的图。 是可学习温度。)
几行就能实现的灵魂代码:
def info_nce(img_emb, txt_emb, tau=0.07): # 两个嵌入都已 L2 归一化, (N, d)
logits = img_emb @ txt_emb.T / tau # (N, N) 相似度矩阵
labels = torch.arange(len(img_emb))
return (F.cross_entropy(logits, labels) + F.cross_entropy(logits.T, labels)) / 2
防坍塌机制:负样本(batch 内其他对)就是排斥力——如果所有嵌入坍到一点,loss 会是 log(N) 而降不下去。代价是需要大 batch(CLIP 用 32768),且假负样本(batch 里恰好有语义相同的图文对)会被错误排斥——已知缺陷,知道即可。
4. DINO:自己教自己,注意力里长出分割
《Self-Distillation with No Labels》(2021):
- 同一张图做多尺度裁剪(global + local crops);
- 教师(学生权重的 EMA 副本,0.4 章 EMA 的思想)看 global view,学生看所有 crops;
- 学生最小化与教师输出分布的交叉熵;
- 防坍塌靠 centering(教师输出减去运行均值,防某类独大)+ sharpening(低温度锐化)——没有负样本,全靠这两招维持输出分布不退化。
成名点:训练完不微调直接看注意力图,物体的分割轮廓自己浮现(这是本章作业的彩蛋)。后续 DINOv2(2023)用数据策展 + 大规模训练把冻结特征推到”万能视觉特征”:分类、深度、分割、检索全线可用——并且成为机器人/具身智能的视觉底座(pi0 等 VLA 模型大量使用 DINOv2 特征,卷5.3 呼应)。
5. 三巨头对比(背下来)
| MAE | CLIP | DINO | |
|---|---|---|---|
| 信号构造 | 遮住重建像素 | 图文配对对齐 | 增强一致性自蒸馏 |
| 数据需求 | 纯图像 | 图文对(不标注) | 纯图像 |
| 防坍塌手段 | 重建目标本身防坍塌 | batch 内负样本 | centering + sharpening |
| 学到什么 | 低/中层补全能力 | 跨模态对齐空间 | 通用视觉特征、分割涌现 |
| 多模态角色 | 预训练思想来源 | VLM 地基 + 检索 + 奖励模型 | VLA/机器人视觉底座 |
三条路线没有胜负:CLIP 赢在”文本锚点”打开了多模态大门;DINO 特征在无文本的具身场景称王;MAE 思想活在生成模型和统一架构里。你未来研究用到哪个,取决于你的题目需要”对齐空间”还是”通用特征”。
6. 自测题
- 自监督和监督学习的本质区别一句话?(监督信号是否由人工标注产生;自监督的”标签”从数据结构中构造)
- MAE 为什么遮 75% 而 BERT 只遮 15%?(图像像素冗余、语言信息密度高;遮罩率应匹配模态冗余度)
- MAE 的解码器为什么可以扔?(重建是训练脚手架,部署只要编码器特征——“训练目标 ≠ 部署需求”的经典案例)
- 对比学习的坍塌是什么?CLIP 和 DINO 各靠什么防?(输出全相同;负样本排斥 / centering+sharpening)
- InfoNCE 里温度 τ 小意味着什么?(分布更尖,难负样本主导梯度——训练后期常见动态调整的原因)
- 为什么 DINOv2 成了机器人底座而不是 CLIP?(具身场景没有文本查询,需要的是稠密、空间敏感的通用视觉特征,而非跨模态对齐)
- 假负样本问题是什么,什么场景更严重?(batch 内本为同类/同义的对被错误推远;细粒度数据集、概念密集的图文对)
7. 动手作业
- 手写
info_nce(第 3 节代码),用随机嵌入验证:完美对齐时 loss→0,全坍塌时 loss≈log(N)——亲手看见坍塌。 - 用 open_clip 加载 CLIP,对一张图做 75% 掩码”提问式”实验:遮住半张图问 CLIP”这是什么”,体会对齐空间对不完整输入的鲁棒与脆弱。
- 用 timm 加载
vit_base_patch16_224.dino,抓最后一层 CLS→patch 注意力画热力图,和 1.4 作业的监督 ViT 对比(DINO 的分割感通常明显更强)。 - 挑战:读 MAE 论文 §3,用三句话向别人解释”非对称设计”省了多少计算、为什么不影响学到的特征质量。
8. 延伸资源
- MAE / CLIP / DINO 三篇原论文——配合李沐《论文精读》对应各期(他全讲过)
- 《Understanding Self-Supervised Learning》类综述——按需查阅
- DINOv2 repo——冻结特征跑深度估计 demo,十分钟见效
1.6 CLIP 精读与 zero-shot 评测实操(第一个完整项目)
本章目标:把 1.5 的 CLIP 思想落到一个完整可交付的项目——用预训练 CLIP 在 CIFAR-10 上做 zero-shot 分类、prompt 集成提分、跨模态检索 demo,写成规范的 repo。这是你作品集的第一块”多模态”砖,也是卷3 理解 VLM 的钥匙。
1. 精读地图:CLIP 论文里该带走什么
1.5 章已讲清目标函数,精读时重点补三块:
- 训练配方:4 亿图文对、batch 32768、可学习温度初始化 0.07(上限钳到 100)、图像增强只有”随机裁剪+flip”(对比学习界花哨增强在此无用)、AdamW+cosine、训 32 epoch 量级。启示:对比学习怕假负样本,增强过度反而破坏图文对语义;
- zero-shot 分类:把分类变成检索——每个类别写一句 prompt(“a photo of a {class}”),编码成嵌入,看图像嵌入和哪个类嵌入最近。prompt 就是分类器的权重;
- prompt engineering 与集成:单个 prompt 在细粒度任务上不稳(“boxer”是人还是狗?),论文对每个类用 80 个模板(“a photo of a big {class}”、“a sculpture of a {class}”…)编码后取平均——集成后 ImageNet 从 63% → 76%。这是本章作业的提分点。
2. 嵌入空间的性质(理解它,才能用好它)
- 余弦相似度:塔输出强制 L2 归一化,内积即余弦。所有检索、打分、分类都建立在”归一化嵌入的内积”这一个操作上;
- 跨模态检索:同一空间里 image↔text 双向检索(以文搜图的商品化技术底座就是它);
- 方向即语义:嵌入空间中的平移/方向对应语义变化(“好照片 vs 差照片”的方向 = 8.2 章美学探针的原理);
- 已知怪癖:对”词序”近乎无感(scrambled words 实验)、计数与空间关系弱、训练分布是英文互联网——评测时永远记住”CLIP 分数是它见过的分布的镜像”。
3. 项目实操:三件事(完整代码)
环境:pip install open_clip_torch(open_clip 是 CLIP 的开源复现集合,学术界事实标准)。
3.1 Zero-shot 分类(CIFAR-10)
import torch, torch.nn.functional as F
import open_clip
from torchvision import datasets, transforms
device = "cuda" if torch.cuda.is_available() else "cpu"
model, _, preprocess = open_clip.create_model_and_transforms("ViT-B-32", pretrained="openai")
tokenizer = open_clip.get_tokenizer("ViT-B-32")
model = model.to(device).eval()
CLASSES = ["airplane", "automobile", "bird", "cat", "deer",
"dog", "frog", "horse", "ship", "truck"]
TEMPLATES = ["a photo of a {}.", "a photo of the {}.", "a blurry photo of a {}.",
"a bright photo of a {}.", "a photo of one {}."] # 先 5 个,作业里扩
# 文本侧:每个类 = 各模板嵌入的平均(再归一化)
with torch.no_grad():
class_emb = []
for c in CLASSES:
toks = tokenizer([t.format(c) for t in TEMPLATES]).to(device)
e = model.encode_text(toks)
e = F.normalize(e, dim=-1).mean(0)
class_emb.append(F.normalize(e, dim=0))
class_emb = torch.stack(class_emb) # (10, 512)
# 图像侧 + 评测
test = datasets.CIFAR10("data", train=False, transform=preprocess)
loader = torch.utils.data.DataLoader(test, batch_size=512, num_workers=4)
correct = total = 0
with torch.no_grad(), torch.autocast("cuda", dtype=torch.bfloat16, enabled=(device=="cuda")):
for x, y in loader:
img = F.normalize(model.encode_image(x.to(device)), dim=-1)
pred = (img @ class_emb.T).argmax(dim=1).cpu() # 余弦最近邻 = 分类
correct += (pred == y).sum().item(); total += y.size(0)
print(f"zero-shot acc: {correct/total:.4f}") # ViT-B/32 通常 0.85~0.90
对照读法:encode_image 是 1.4 的 ViT;encode_text 是 1.3 的 decoder-only Transformer(取 EOT 位置的输出);img @ class_emb.T 是 1.2 的注意力打分函数去掉了 softmax(归一化内积)。三个前章在这里会师。
3.2 Prompt 集成实验(提分点)
把 TEMPLATES 扩到 20+ 个(模仿论文的 80 个:光照、风格、尺寸、视角…),记录 acc 曲线。观察收益递减的位置——写进 README,这就是你的第一份”实验报告”。
3.3 跨模态检索 demo
准备 100 张图 + 自定义查询(“a dog on the beach”),编码后 img_emb @ query_emb 排序,matplotlib 拼出 top-5 结果图。这个 demo 在面试里比分类数字更有说服力。
3.4 repo 规范(作品集标准)
clip-zero-shot/
├── README.md # 结果表 + 曲线图 + 三个发现(用数字说话)
├── requirements.txt
├── src/
│ ├── zeroshot.py # 3.1
│ ├── prompt_sweep.py # 3.2
│ └── retrieval.py # 3.3
└── assets/ # 检索结果图
4. CLIP 的产业角色(为什么值得花一周)
- 数据引擎:LAION 用 CLIP 给数十亿图文对打分过滤 → 文生图模型的训练集(你训练的 SD/FLUX 的血统里都有 CLIP);
- 奖励模型底座:美学评分(8.2 章)、人类偏好对齐(PickScore 等)全在 CLIP 空间上建;
- VLM 视觉塔:早期 LLaVA 直接用 CLIP ViT 当视觉编码器(卷3.2);
- 内容审核与搜索:以文搜图、违规内容向量分类,工业界每天在跑。
一句话:CLIP 是多模态产业的”公共基础设施”,也是你科研里最常用的预训练底座。
5. 自测题
- zero-shot 分类为什么可行?“分类器权重”是什么?(对齐空间使图文可比;各类 prompt 的嵌入向量)
- 为什么 prompt 集成有效、收益为何递减?(多视角消解 prompt 偏差;覆盖同类语义后饱和)
- 温度可学习化在训练中起什么作用?(自适应难度:早期拉近粗对齐,后期聚焦难样本)
- CLIP 在计数/空间关系上为什么弱?(训练目标是全局对齐,监督信号不要求局部结构理解)
- 用 CLIP 做数据过滤的系统性风险是什么?(过滤偏差会烙进下游模型——“谁定义了好数据”成为权力,也是研究题)
- batch 32768 除了算力还防什么问题?(对比学习需要足够负样本密度;小 batch 排斥力不足,学不到细粒度区分)
6. 动手作业(项目交付标准)
- 跑通 3.1,基线 acc 记入 README;
- prompt sweep:5 → 20 → 50 模板三档 acc 曲线(wandb 或 matplotlib 图贴 README);
- 检索 demo 出 5 张结果拼图;
- 加做:zero-shot 迁移到你自己挑的细粒度数据集(如 8.1 的 WikiArt 流派分类,21 类),对比论文报告的水平——顺手完成 8.1 作业 2 的升级版;
- README 里写一节”失败与怪癖”:找到至少 1 个 CLIP 分类翻车的例子并分析原因(用 1.5/8.1 的语言)。
7. 延伸资源
- CLIP 论文(Learning Transferable Visual Models From Natural Language Supervision)+ 李沐精读一期
- open_clip repo + 文档——model zoo 里 ViT-B/32 → ViT-L → SigLIP 逐个玩
- LAION-5B 论文泛读——数据引擎视角看 CLIP
1.7 SAM 与分割基础模型:提示式视觉
本章目标:吃透 SAM(Segment Anything)——它不只是分割模型,而是”提示式交互视觉”这一新范式的开端,也是数据引擎自举的经典案例。学完标准:能画出 SAM 三件套架构并解释”为什么这么设计”,会用 box/point prompt 完成实操,知道 SAM 2 把什么搬到了视频。
1. SAM 是什么:分割界的 GPT 时刻
Meta(2023)的三件事:① SA-1B 数据集:1100 万张图、11 亿个掩码——史上最大分割数据;② 可提示范式:模型接受点/框/粗掩码作为”提示”,输出对应物体的分割——像 GPT 接受 prompt 输出文本一样;③ 零样本泛化:没见过的物体/域(医学影像、素描)也能分——通用性首次出现在分割任务上。
范式意义:CV 从”每个任务训一个模型”转向”一个基础模型 + 任务提示”。这与 LLM 的 in-context learning 是同一次思想迁移(1.5 自监督 → 基础模型 → 提示交互,视觉侧的完整三连)。
2. 架构三件套(设计的聪明之处)
图像编码器(ViT-H,MAE 预训练,最重)→ 图像嵌入(一张图算一次)
提示编码器(点/框/掩码 → 编码,极轻) ↘
掩码解码器(轻量双向 attention,~50ms)→ 分割掩码(可多次交互)
关键设计:重的一端(图像编码)与轻的一端(解码)解耦——交互场景下图像嵌入缓存复用,用户每点一下只需 50ms 重解码。这是”为交互而设计的架构”教科书案例:把昂贵的计算放在不变量上,把便宜的计算放在交互变量上(KV cache 是同一哲学,2.3)。
训练:三阶段(监督→数据引擎自举:模型辅助标注→新数据回灌→模型更强,5.2 数据为中心的经典案例)→RL 式微调对齐交互。
3. SAM 2(2024):提示式视频分割
把”分割一切”搬到视频:流式记忆——当前帧通过 memory attention 关注之前的关键帧记忆与提示记忆,逐帧传播掩码;图像与视频统一进一个模型。能力:track anything——点一下视频里的物体,全程跟住(遮挡后还能找回)。实用地位:视频标注、VLA 数据采集(5.3 的演示数据标注)、特效制作的底层工具。
4. 家族与应用接口
- Grounded-SAM:文本开集检测(Grounding DINO)出框 → SAM 精细分割——“说一句话分出指定物体”的标准管线(5.6 agent 的感知件);
- MedSAM:医学域微调——基础模型 + 领域数据的典型配方;
- SAM-HQ:边界质量增强;MobileSAM/FastSAM:端侧化(5.8 的效率路线);
- 你的方向:线稿提取(8.4 画师管线的自动前置步骤)、文物图像的自动分割编目(8.8)、生成图的结构分析(A3 鉴别的特征源)。
5. 实操十分钟
from segment_anything import sam_model_registry, SamPredictor
sam = sam_model_registry["vit_b"](checkpoint="sam_vit_b.pth").cuda()
predictor = SamPredictor(sam)
predictor.set_image(image_rgb) # 重计算只做一次
masks, scores, _ = predictor.predict(
box=np.array([x1, y1, x2, y2]), multimask_output=True) # 轻解码随便点
自动全图分割用 SamAutomaticMaskGenerator(网格撒点提示)——批量产出训练数据的工具形态。
6. 自测题
- SAM 的三件套里哪个最重?交互设计怎么利用这一点?(图像编码器;嵌入缓存、只重跑轻解码——“贵计算放不变量”)
- 可提示范式的意义?(一个模型+任务提示替代每任务一模型——LLM in-context 思想的视觉迁移)
- SA-1B 的掩码哪来的?(数据引擎自举:模型辅助标注→回灌→迭代的经典闭环)
- SAM 2 用什么机制做视频跟踪?(流式 memory attention——当前帧查历史记忆)
- Grounded-SAM 的两级管线是什么?(文本开集检测出框 + SAM 精细分)
- 它对你方向的三处接口?(线稿提取/文物分割编目/生成图结构分析)
7. 动手作业
- 完成第 5 节实操:对一张名画(8.1 的素材)做 box 提示分割,把主体抠出;
- 用 AutomaticMaskGenerator 对同一张画全图分割,数一数掩码数量与平均面积——“细节密度”的另一种测量(对照 8.1 映射表);
- 跑 SAM 2 的视频 demo:给一段水墨运笔视频 tracking 笔尖——感受”提示式”在时序上的延伸;
- 挑战:读 SAM 论文 §3 的数据引擎部分,画自举闭环图——对照 5.2 写 200 字。
8. 延伸资源
- SAM / SAM 2 论文——各精读一遍(SAM 的消融与数据引擎章节是精华)
- Grounded-SAM repo——组合管线的工程范本
- segment_anything 官方 notebook——十分钟上手
1.8 检测与分割极简史:知道即可的一章
本章定位:诚实的定位——这是全书最薄的一章。检测/分割的传统内容已工业化(1.1 §6 的存量市场判断),你需要的只是:任务定义、演化脉络、几个绕不开的名字(U-Net!),以及评测常识。学完标准:30 分钟后能在任何对话里不掉链子,并把注意力留给真正要紧的 U-Net。
1. 任务定义一张表
| 任务 | 输出 | 例子 |
|---|---|---|
| 分类 | 全图一个标签 | 猫/狗 |
| 检测 | 框 + 类别 | 找出图里所有的行人 |
| 语义分割 | 每像素类别(不分实例) | 所有”路”的像素 |
| 实例分割 | 每个物体的像素掩码 | 每个行人各自的轮廓 |
| 全景分割 | 语义 + 实例合体 | 前景逐物体 + 背景逐类 |
评测常识:检测用 mAP(按 IoU 阈值判定命中,对置信度排序算精度-召回曲线下面积);分割用 IoU/mIoU(交并比)。知道”IoU 0.5 是及格线惯例、mAP@50 vs mAP@50:95 的区别”即可。
2. 检测极简四幕剧
- 传统时代:HOG+SVM、DPM——滑窗+手工特征(1.1 存量市场的注脚);
- 两阶段 CNN 时代:R-CNN 家族(选择性搜索/Region Proposal Network 先提候选框,再分类精修)——精度高、速度中;Faster R-CNN 是两阶段的完成体;
- 单阶段时代:YOLO/SSD——一次前向直接出框(回归式),快到能上嵌入式——工业部署至今的主力(巡检/安防/车载);Focal Loss(RetinaNet)解决正负样本失衡,是训练技巧史的名场面;
- Transformer 时代:DETR——把检测改写成”集合预测”:固定 100 个 object query(可学习的”格子”)查图像特征,输出恰好 100 个(类别, 框),用匈牙利匹配做一对一监督——彻底删掉了 NMS 后处理和候选框概念,架构优雅;后续 DINO-DETR 等把精度做到全面领先。
现状一句话:部署看 YOLO 系,研究看 DETR 系;两者你都不必复现。
3. 分割极简四站
FCN(全卷积,像素级预测的开山)→ U-Net(★全书级重要)→ Mask R-CNN(检测+实例分割合体)→ SAM(1.7 的基础模型时代)。
为什么 U-Net 单独加星:编码器-解码器 + 跳跃连接的结构(4.4 §2.2 讲过),是医学影像的常青主力,也是 SD 扩散 U-Net 的直系祖先——“学会了 U-Net,半只脚踏进医学影像 + 一只脚站在扩散模型里”。它的思想(下采样提语义、上采样还细节、跳跃连接直通细节)在 4.4 已拆解,这里只需记住名字与血缘。
4. 与你主线的接口
- 检测 → grounding:VLM 的指框能力(Qwen-VL 系,3.5)本质是”语言条件检测”——DETR 的 query 思想与 LLM 的结合是当前开放词汇检测的研究面;
- 分割 → SAM 时代:1.7 已讲;传统分割(U-Net 系)仍统治医学影像——AI for Science(5.7)的主要工具;
- 对你的行动建议:知道即可(本章定位),把省下的时间投给卷2/卷3——这是本笔记”传统只留薄底”原则的最后一次执行。
5. 自测题
- 语义/实例/全景分割的区别一句话?(逐类 vs 逐物体 vs 两者合体)
- 两阶段与单阶段检测的取舍?(精度 vs 速度——候选框精修 vs 直接回归)
- DETR 的”集合预测”新在哪?(固定 query + 匈牙利一对一匹配,删掉 NMS 与候选框)
- U-Net 为什么单独加星?(医学主力 + 扩散 U-Net 祖先——跳跃连接思想贯穿两域)
- mAP 和 IoU 各测什么?(排序后的命中精度 / 掩码重叠度)
- 本章为什么敢于”薄”?(传统检测分割已工业化——你的增量在多模态,不在 YOLO 调参)
6. 动手作业
- 用
ultralytics(YOLO)跑一张图的目标检测,10 分钟体验”工业现成品”; - 手画 U-Net 结构图,标注每层分辨率与跳跃连接——为 4.4 的 SD 复习做准备;
- 用 open 数据(如 COCO 的 20 张子图)手算 IoU 与 mAP@50(numpy 实现)——评测常识的肌肉记忆。
7. 延伸资源
- 《Object Detection in 20 Years: A Survey》——四幕剧的完整版(选读)
- U-Net 原论文(15 分钟)——血缘关系值得
- DETR 论文 §1–2——集合预测的思想
1.9 图像形成与相机模型:给 3D/具身留的几何底座
本章目标:补上”光怎么变成像素、像素怎么回到空间”的物理与几何底座——5.5 的 COLMAP、4.7 的视角控制、5.3 的机器人相机,全部站在这块地基上。学完标准:能写出针孔投影公式并解释内外参的作用,知道 COLMAP 在解什么问题。
1. 图像形成:光到像素的三段旅程
场景反射的光 → 镜头(聚焦,光圈控制景深)→ 传感器(曝光:快门时间 × 光圈 × ISO 的组合)→ 数字化(拜耳滤色阵列 + 去马赛克 + gamma 编码)。
两个与生成/处理直接相关的点:① 曝光三角(光圈/快门/ISO)决定了运动模糊、噪点、景深——生成模型学到的”摄影感”本质是这些物理参数的分布(prompt 里的 “shallow depth of field, f/1.4” 就是在索要光圈物理);② gamma/sRGB 编码(8.1 §2.1 已讲)是”人眼非线性”的存储妥协——处理图像的数学最好在线性光空间做。
2. 针孔相机模型:三维到二维的投影
空间点 (相机坐标系)投到像素平面的完整链条:
- 内参 K(相机自己的属性):焦距 (换算成像素单位)与主点 (光轴落点);
- 外参 (相机在世界里的位姿):旋转 + 平移——NeRF/3DGS 训练需要逐张照片的 ,COLMAP 的核心工作就是从照片对里把它们恢复出来(5.5 的伏笔在此收线);
- 齐次坐标:用多一维的坐标让投影变成一次矩阵乘(平移也能线性表达)——机器人学/3D 视觉的通用语言,习惯即可。
畸变:真实镜头不是理想针孔(桶形/枕形畸变),标定即求解畸变系数并在投影前后校正——手机相机的”超广角校正”就是它。
3. 多视角几何的最小概念集(概念级,不推导)
- 对极几何:两个相机看同一点,该点在各视图的投影位置受”对极约束”限制——这是不需要 3D 点就能从 2D 对应关系恢复相机相对位姿的钥匙(essential/fundamental 矩阵,概念知道即可);
- 三角化:两个已知位姿的相机 + 同一点的两个投影 → 交出该点的 3D 位置——重建的原理本体;
- SfM(Structure from Motion)/COLMAP:特征匹配(1.1 的”模板匹配”回归!)→ 对极约束求位姿 → 三角化出稀疏点云 → 光束法平差(bundle adjustment,全局优化)。5.5 作业里你跑的 COLMAP 就是这套;
- 对偶问题记住一句话:已知位姿求点是三角化,已知点求位姿是定位,都不知道就交替着来(SfM)。
4. 与你主线的四个接口
- 3D 管线(5.5):COLMAP 位姿是 NeRF/3DGS 的输入——现在你知道它内部的几何;
- 生成模型的视角控制:相机的 与焦距是物理意义上的可控生成旋钮(相机轨迹控制视频、焦距控制景深)——比”换视角的 prompt”硬核得多的控制量;
- 具身(5.3):机器人头上的相机内外参标定是”手眼标定”问题——VLA 部署的第一天就会遇到;
- 艺术(8.x):线性透视法的数学就是投影几何(8.1 §5 的文艺复兴透视)——达芬奇和针孔模型写的是同一套数学。
5. 自测题
- 内参和外参各是什么属性?谁需要逐图估计?(相机固有属性 / 相机在世界中的位姿;外参逐图——SfM 的产出)
- 为什么投影要用齐次坐标?(平移纳入线性变换——一次矩阵乘完成投影)
- 对极约束”强”在哪?(不需要任何 3D 信息就能约束两视图对应关系并恢复相对位姿)
- 曝光三角的三个物理量各控制什么视觉效果?(光圈→景深;快门→运动模糊;ISO→噪点)
- 生成模型里”相机参数作为控制旋钮”比 prompt 好在哪?(物理精确、连续可微、与 3D 管线兼容)
- COLMAP 的四步流水线?(匹配→对极求位姿→三角化→光束法平差)
6. 动手作业
- 用 OpenCV 对手机拍的一张棋盘格做相机标定(
cv2.calibrateCamera),读出你手机的内参和畸变系数; - 用标定结果对一张广角照片做去畸变(
cv2.undistort),前后对比; - 在 5.5 的 COLMAP 输出里找到
cameras.txt/images.txt,把某一行的外参翻译成”相机的位置与朝向”(人话); - 挑战:手写针孔投影(numpy 十行),把一个立方体的 8 个顶点投影到图上并连线渲染——你的第一个 3D 渲染器。
7. 延伸资源
- 《Multiple View Geometry in Computer Vision》(Hartley & Zisserman)——圣经级参考(选读第 1、6 章)
- OpenCV 相机标定官方教程——工程直达
- COLMAP 文档 §Getting started——配合 5.5 作业
2.1 语言模型前史:n-gram → RNN → 注意力(20 分钟走完 30 年)
本章目标:理解”预测下一个词”为什么从 1950 年的玩具问题变成今天的圣杯任务,以及 GPT 范式赢在哪几个关键决策上。学完标准:能用五分钟向别人讲清”从 n-gram 到 ChatGPT 发生了什么、每一步解决了上一个的什么死穴”。
1. 任务定义与它的特殊性
语言模型估计 。用概率的链式法则,整句概率可以分解为逐词条件概率的连乘:
这个任务看起来平淡,却同时满足三个苛刻条件:
- 数据无限:互联网上任何文本都是训练样本(自监督,1.5 章思想的文字版);
- 目标极简但要求全面:预测“‘明天开盘后,上证指数最可能’ 的下一个词”,需要语法、事实、逻辑、世界知识的全部;
- 评测自然:loss / 困惑度(perplexity = ,直觉是”模型眼里每个位置平均有多少个候选词在纠结”)随能力单调改善。
“压缩即智能”:预测得好 = 用模型压缩文本压得好(算术编码的联系)。这是理解”为什么一个 next-token 任务能涌现推理”的最好心智模型——也是 Hutter Prize 一直奖励压缩算法的原因。
2. n-gram 时代(1948–2000s):统计机器
Shannon 用马尔可夫假设开山:只看前 n−1 个词,数语料里下一词的频率,加平滑处理没见过的组合。问题立现:
- 组合爆炸:n=3 时常见词组合已数不过来,n=5 时几乎所有组合都稀疏;
- 泛化失败(根子):“the cat sat” 和 “the dog sat” 的后续统计完全隔离——明明语义相似,统计上互不相干。
但 n-gram 留下了两笔遗产:next-token 这个任务本身,和困惑度这个指标。
3. 神经语言模型(2003)与 word2vec(2013):词变成向量
Bengio 的神经 LM 给每个词一张稠密向量(embedding),用神经网络输出下一词分布。关键贡献一句话:语义相似的词向量相似 → 它们的统计自动共享——“cat” 和 “dog” 的嵌入接近,“the __ sat” 的预测互相支援,n-gram 的泛化死穴被解决。
word2vec 把嵌入训练做成独立任务并发现:向量算术 。嵌入空间 = 语义几何——这个思想一路延续:CLIP 的图文对齐空间、8.2 章在嵌入空间里找”美丑方向”,都是它的后代。
4. RNN/LSTM(≈2003–2017):循环与门控
:理论上无限长上下文,十年统治翻译/语音。LSTM 用门控(记忆细胞 + 输入/遗忘/输出门)缓解梯度消失。但 1.2 章讲过的两大死穴没救:顺序计算不可并行(GPU 干瞪眼)+ 长程依赖衰减(信息要路过每一步)。
5. 2017–2022:五年定乾坤
| 年份 | 事件 | 一句话评语 |
|---|---|---|
| 2017 | Transformer | 注意力解决 RNN 双死穴(1.2–1.3) |
| 2018 | GPT-1 / BERT | 路线之争开始:生成式预训练+微调 vs 双向掩码刷榜 |
| 2019 | GPT-2 | 赌注升级:“语言模型是无监督多任务学习者”——翻译/摘要可以从 next-token 里涌现 |
| 2020 | GPT-3 | 175B + few-shot(in-context learning);scaling law 出炉,算力换智能变成可计算的投资 |
| 2022 | ChatGPT | GPT-3.5 + SFT + RLHF:把”能力”变成”产品”(对齐是临门一脚,2.7 详述) |
理解这段历史的关键:2018 年时行业主流押的是 BERT(理解任务刷榜快、训练便宜),GPT 线是少数派押注”生成式 + 规模”。三张牌——自回归目标、规模定律、指令对齐——2020 年起逐一验证,才有 2022 的引爆。读论文时要练习识别”哪个赌注被时间验证了”,这是研究品味的原料。
6. Scaling law 预告(2.4 详讲)
Kaplan 等(2020)发现:test loss 随参数量、数据量、算力呈光滑幂律,跨 7 个数量级成立。它把”更大的模型会更好”从信仰变成工程预算表——这是资本敢投百亿建集群的数学依据。Chinchilla(2022)修正了配比(每个参数约 20 token 最优)。对你的启示:做实验先在小规模建立趋势线,再谈放大。
7. 自测题
- 链式法则把句子概率分解成什么?这和模型训练目标什么关系?(逐词条件概率连乘;模型逐位置优化 即等价优化整句似然)
- n-gram 的根子问题是什么?谁解决的?(相似上下文统计不共享;稠密嵌入)
- perplexity=2^loss 的直觉含义?(模型每步平均在多少个等概率候选中犹豫)
- BERT 和 GPT 的路线差异各是什么?为什么 GPT 线最终通向大模型?(掩码双向刷理解榜 vs 自回归生成;生成即通用接口 + 自回归目标数据利用率高)
- ChatGPT 相比 GPT-3 缺哪块拼图补上了?(指令微调 + 人类偏好对齐——能力变可用)
- “压缩即智能”怎么理解?(预测好等价于压缩好;压缩要求抓住数据生成规律)
- scaling law 为什么是工业决策的定心丸?(损失可外推 → 投资回报可预算)
8. 动手作业
- 用 gensim 训一个 word2vec(或加载现成中文向量),复现若干组向量算术,找一个失败案例并分析为什么(词频、多义性)。
- 手算:模型在词表 5 万、uniform 分布下的困惑度是多少?(=词表大小 50000;这就是”模型学到任何东西”的起点线)
- 费曼测试:不看笔记,向同学(或录音)讲 5 分钟”n-gram→GPT”时间线,讲不清的地方回炉。
9. 延伸资源
- 《Speech and Language Processing》(Jurafsky & Martin) 第 3、9 章——n-gram 与神经 LM 的系统版
- 李沐《论文精读》GPT-1 / GPT-2 / GPT-3 三连——历史现场感
- Shannon《A Mathematical Theory of Communication》(1948)——选读,感受源头
2.2 BPE tokenizer 原理与实现
本章目标:搞清模型真正”看到”的东西——token。tokenizer 是所有诡异行为(数字比较、字母计数、计费差异)的第一嫌疑人。学完标准:能手写 BPE 的训练与编码,能用 tiktoken 检查任何文本的 token 边界,能解释”strawberry 数不出 r”的机理。
1. 为什么需要 tokenizer,以及三条路线
模型做的是对离散符号的 softmax(0.1 章的分类分布),输入必须变成有限词表里的 id。三个候选粒度的 trade-off:
| 粒度 | 词表 | 序列长度 | 缺点 |
|---|---|---|---|
| 词 | 巨大,且总有新词(OOV) | 短 | 开放词汇不可行 |
| 字符 | 极小(~百级) | 极长 | 序列长 → 注意力平方爆炸(1.2 的账) |
| 子词(BPE) | 数万–15万 | 中 | ——现代共识 |
子词的哲学:常见序列合并成单元,罕见内容退回字节。英文单词 ≈ 1 个 token,生僻词拆成几块,任何语言任何符号最终都有字节兜底——永不出 OOV。
2. 字节级 BPE:算法(必须能白板实现)
BPE(Byte Pair Encoding)本质是贪心的数据压缩:
训练(从语料学”合并表”):
- 把所有文本转成 UTF-8 字节序列(起点:256 个基础 token);
- 统计当前序列中相邻 token 对的出现频率;
- 把最高频的一对合并成新 token(id = 257, 258, …),记录到合并表;
- 重复第 2–3 步,直到词表达到目标大小(如 15 万)。
编码(推理时用):把输入转成字节,按训练时学到的合并顺序逐条贪心重放合并。
极简实现(~40 行,Karpathy minbpe 的骨架):
def merge(ids, pair, new_id):
out, i = [], 0
while i < len(ids):
if i < len(ids) - 1 and (ids[i], ids[i+1]) == pair:
out.append(new_id); i += 2 # 命中:两个 token 换成一个
else:
out.append(ids[i]); i += 1
return out
def train_bpe(text, vocab_size):
ids = list(text.encode("utf-8")) # 起点永远是 0..255 字节
vocab = {i: bytes([i]) for i in range(256)}
merges = {}
for step in range(vocab_size - 256):
cnt = {}
for a, b in zip(ids, ids[1:]): # 1. 统计相邻对频率
cnt[(a, b)] = cnt.get((a, b), 0) + 1
best = max(cnt, key=cnt.get) # 2. 最高频对
new_id = 256 + step
merges[best] = new_id # 3. 记入合并表
vocab[new_id] = vocab[best[0]] + vocab[best[1]]
ids = merge(ids, best, new_id) # 4. 全量重放
return merges, vocab
def encode(text, merges):
ids = list(text.encode("utf-8"))
for pair, new_id in merges.items(): # 按学习顺序贪心重放
ids = merge(ids, pair, new_id)
return ids
def decode(ids, vocab):
return b"".join(vocab[i] for i in ids).decode("utf-8", errors="replace")
细节红线:合并表必须按学习顺序重放(顺序即优先级);errors="replace" 处理”半个中文字”的截断(token 边界可能切开 UTF-8 多字节字符)。
3. tiktoken 实操:把 token 变成看得见的东西
import tiktoken # pip install tiktoken
enc = tiktoken.get_encoding("o200k_base") # GPT-4o 系词表
ids = enc.encode("多模态大模型是真香")
print(ids) # 每个 id 一个 token
print([enc.decode([i]) for i in ids]) # token 边界可视化
print(len(enc.encode("一句话"))) # token 数 = 计费/上下文的单位
必做观察:中文字符通常 1 字 = 1~2 token(国产模型用大中文词表压到约 1.5 字/token——Qwen 15.2 万词表对中文更省,这是”国产模型中文便宜”的底层原因之一);英文平均 1 词 ≈ 1.3 token;代码和数字切分有自己的脾气(下节)。
4. tokenizer 造成的经典翻案(懂机理,见怪不怪)
- “9.11 和 9.9 哪个大”:老 tokenizer 把数字按 2–3 位一切,模型看到的可能是
[9.1][1]vs[9.9]——它做的是 token 序列比较,不是数值比较。现代 tokenizer 改进数字切分 + 训练数据加了算术,但机理要懂; - “strawberry 有几个 r”:模型看到的是 2–4 个 token 的 id,不是 10 个字母——字符级信息被 tokenizer 抹掉了。它必须靠训练里学到的”间接知识”回答;
- 特殊 token 注入:
<|endoftext|>这类保留 token 拥有特权(终止符、系统标记)。用户输入里出现它们可能逃逸出当前角色——所以推理框架把 special token 与普通文本分开编码(tiktoken 的encode(..., allowed_special=)参数就是干这个的); - 中文/代码的序列长度差:同样的内容换 tokenizer,上下文占用和 API 费用差几十个百分比。
一句话:模型的一切能力都作用在 token 上,token 是 tokenizer 决定的——分析任何诡异行为,先看 token 边界。
5. 词表大小的权衡
- 词表大 → 序列短(省注意力平方的钱)、中文友好;代价是嵌入层参数大(,15 万词表 × 4096 维 ≈ 6 亿参数,比很多模型还大)和 softmax 计算大;
- 词表小 → 模型小序列长;
- 现代主流:12.8 万–15.2 万(LLaMA 128k,Qwen 152k),多语料时代的甜点区。
6. 自测题
- BPE 训练和编码各自在干什么?(训练学合并表:反复合并最高频相邻对;编码按学习顺序贪心重放)
- 为什么字节级起点保证”永不出 OOV”?(任何 UTF-8 都是字节序列,256 基础 token 兜底)
- “半个中文字”是什么现象?(token 边界切开 UTF-8 多字节字符;decode 用 errors=“replace”)
- 为什么数字和字母计数是 LLM 的经典弱项?(字符级结构被 token 化抹掉,模型看到的是块 id)
- 词表加大的两个收益两个代价?(序列短/中文省 token vs 嵌入参数大/softmax 开销)
- special token 为什么要和普通文本分开编码?(防用户输入伪造终止符/系统标记越权)
7. 动手作业
- 用第 2 节代码在一段中文+英文混合文本上训练 BPE(vocab_size=512),decode 自己的 encode,验证无损往返;
- 用 tiktoken 分别统计:同一段中文新闻、同长度英文新闻、一段 Python 代码的 token 数,算”字符/token 比”并解释差异;
- 找出
o200k_base里”多模态”三个字的切分边界,画出每个 token 的字节构成; - 挑战:读 Karpathy《Let’s build the GPT Tokenizer》前半段,把你的实现升级为支持 special token 的版本。
案例 · BPE 三步合并全记录
语料(词频):low ×3,lower ×1,slower ×1(词尾统一加 </w> 标记,从 256 个字节 token 起步)。
| 轮次 | 统计相邻对频次 | 最高频对 | 合并动作 | 词表大小 |
|---|---|---|---|---|
| 1 | l+o 出现 5 次(low×3 + lower×1 + slower×1) | (l, o) | 新 token lo | 257 |
| 2 | lo+w 出现 4 次(low×3 + lower×1) | (lo, w) | 新 token low | 258 |
| 3 | e+r 出现 2 次(lower + slower) | (e, r) | 新 token er | 259 |
三轮之后,low 已是单个 token;lower 只差最后一并(low+er → lower,频次 2,第 4 轮完成)。
读出 BPE 的品格:高频模式永远优先获得 token 席位——常见词先被”压缩成词”,罕见组合后合并。词表大小就是压缩轮数的预算:15 万词表 = 允许 15 万次贪心合并。中文同理,“的""是”这类高频字会极早合并成整字 token——这就是 2.3 说”国产大词表对中文更省”的机理演示。
8. 延伸资源
- Karpathy《Let’s build the GPT Tokenizer》——与本章一一对应
- minbpe repo(~100 行的生产级参考实现)
- tiktoken repo / HuggingFace tokenizers——工业实现(Rust 底座)
2.3 GPT 架构工程版:从 TinyGPT 到 nanoGPT
本章目标:1.3 章你造出了”教学版”GPT;这一章做工业版升级清单——现代开源模型(LLaMA/Qwen)相对教科书版本的每一处改动及其理由,外加推理侧最重要的两件事:KV cache 与 prefill/decode 两阶段。这是读开源模型源码(卷3 的 Qwen-VL/InternVL)前的最后一站。
1. 升级清单:教学版 → 现代开源版
| 组件 | TinyGPT(1.3) | 现代模型 | 为什么改 |
|---|---|---|---|
| Norm | LayerNorm | RMSNorm(Pre-Norm + final norm) | 砍掉均值中心化,少一半算术,效果不掉(0.3) |
| 位置编码 | 可学习绝对 | RoPE | 相对位置、可外推、长上下文友好(1.3) |
| MLP | Linear(4d)+GELU | SwiGLU(中间维 ≈ 8d/3) | 门控结构实验更优,降维对齐参数量 |
| 偏置 | 有 | 全删(除个别) | 省 ~1% 参数且训练更稳(PaLM 观察) |
| 注意力 | 手写 softmax | F.scaled_dot_product_attention(FlashAttention 内核) | 优化显存 IO 而非数学(1.2) |
| KV 结构 | MHA | GQA(分组共享 KV 头) | 本章 §3——KV cache 显存 |
| 精度 | fp32 | bf16 AMP + grad clip 1.0 | 0.4 章四件套 |
| 稳定件 | —— | QK-Norm(新趋势) | 大模型 loss spike 防治,Qwen3 等在用 |
读源码的预期:卷3 你打开 Qwen-VL 源码时,逐项对号入座——所有”新东西”你都已见过。
2. nanoGPT 精读地图
nanoGPT(Karpathy)的三个文件对应你已经掌握的三块知识:
model.py:1.3 的 Block + 工业化细节。值得抄的两个初始化 trick:所有权重 ;残差路径上的输出投影(c_proj)再乘 ——让残差流方差不随深度累积(GPT-2 原版技巧,解释了”为什么深层初始化要按层数缩放”);train.py:0.2+0.4 章训练循环的全配置化版本。配方:AdamW(=0.95,非默认 0.999——大模型经验值)、weight decay 只作用在 2 维矩阵参数(1 维的 norm/bias 不 decay——“参数形状决定 decay 与否”是行规)、grad clip 1.0、warmup+cosine、bf16;configurator.py:key=value 文本覆盖配置的小机制——工程品味样本,10 分钟读懂。
3. KV cache:推理为什么必须缓存
问题:自回归生成第 个 token 时,因果 mask 意味着历史 token 的 K、V 不会变。朴素做法每步都重算全部历史的前向——生成 个 token 要 次注意力计算,浪费一倍以上。
方案:把每层的 K、V 缓存下来,每步只算最新一个 token 的 q/k/v 并追加:
def step(x_new, cache): # x_new: (B, 1, d) 只喂最新 token
q = Wq(x_new); k = Wk(x_new); v = Wv(x_new)
cache.k = torch.cat([cache.k, k], dim=1) # 沿序列维追加
cache.v = torch.cat([cache.v, v], dim=1)
att = softmax(q @ cache.k.transpose(-2,-1) / sqrt(dh)) @ cache.v # 新 q 看全部历史 K,V
return Wo(att)
显存的账(必须会算):KV cache 大小 = 。
例:7B 模型(L=32, d=4096, fp16, MHA)单条 4k 上下文:——比权重还重只是时间问题(10 条并发 = 21GB,一张卡直接爆)。
GQA(Grouped-Query Attention)就是为此而生:Q 保留全部头,K/V 只留 1/4 的头、组内共享——7B 例子里 从 4096 降到 1024,cache 变 0.54GB,省 4 倍,质量损失极小。LLaMA-2 70B 起几乎所有开源模型标配。MQA(1 组)更省但掉点,GQA 是甜点。
4. Prefill 与 Decode:两种截然不同的负载
推理分两阶段,瓶颈完全不同(这是 2.8 推理优化和 vLLM 的理论根基):
- Prefill:一口气处理整个 prompt(并行,1.2 章的注意力矩阵大展拳脚)。compute-bound——GPU 算力打满,越强的卡越快;
- Decode:逐 token 生成,每步都把全部权重和 KV cache 从显存读一遍、却只做一次小矩阵乘。memory-bound——GPU 算力大量闲置,瓶颈是显存带宽。
Decode 的 memory-bound 带来反直觉结论:一个 batch 里塞 32 个并发请求,总耗时和 1 个几乎一样(权重只需读一次,32 个请求分摊)——这就是推理服务商”并发摊薄成本”的经济学,也是 vLLM 持续批处理(continuous batching)存在的理由。
5. 实操路线(寒假)
- 跑通:
git clone nanoGPT,先跑shakespeare_char配置(笔记本 CPU 都行,10 分钟出”伪莎翁”)——把 1.3 的 TinyGPT 和它逐行 diff,找出全部工业化差异; - 改造:给 nanoGPT 换上 RMSNorm + GQA(各一次 commit),对照 loss 曲线验证”不掉点”;
- 不推荐:复现 GPT-2 124M 全量预训练(数千 GPU 小时)。看它的启动脚本和日志即可——知道全量预训练长什么样,和亲手做一次,价值不同;学生阶段把卡留给微调实验。
6. 自测题
- KV cache 为什么有效?哪些张量在生成过程中不变?(因果性保证历史 K/V 不变;只增量计算新 token)
- 算一遍:你训的 7B LoRA 模型,8 条并发 × 8k 上下文,MHA 的 KV cache 总量?(2×32×4096×8192×8×2B ≈ 34GB——必须 GQA)
- GQA 省的是 Q 还是 KV?为什么省 KV 就够了?(KV;cache 只存 K/V,Q 是当步临时的)
- prefill 和 decode 各是什么瓶颈?对硬件选择意味着什么?(compute-bound / memory-bound;decode 阶段带宽比算力重要)
- 为什么推理服务商欢迎大 batch?(decode 阶段权重读取被多请求摊薄,吞吐近线性涨)
- AdamW 的 β₂ 从 0.999 改 0.95 是什么逻辑?(大模型梯度噪声大、二阶动量窗口过长反而钝——经验修正,注意”默认值不是圣旨”)
7. 动手作业
- 完成第 5 节的 nanoGPT 两步(跑通 + RMSNorm/GQA 改造),diff 报告写进 repo;
- 手写带 KV cache 的推理循环(在 1.3 TinyGPT 上),验证输出与朴素逐 token 前向逐位一致——cache 的正确性测试;
- 用
torch.profiler对比朴素 vs cache 版的每 token 耗时; - 算账题:Qwen3-VL 4B(假设 L=36, d=2560, GQA n_kv=8, bf16)单条 32k 视觉上下文的 KV cache 是多少 GB?这张卡还装得下权重吗?(约 2×36×640×32768×2B ≈ 3GB;权重 8GB——装得下,这就是小模型在端侧的底气)
案例 · 数值:把 KV cache 的账算到底
案例:7B 模型的 KV cache,从公式到 GiB
设 L=32 层,d=4096,MHA(d_kv=4096),fp16(2 字节),单条序列 4096 token:
换 GQA(8 组 KV 头 → d_kv=1024):。
再上强度:16 条并发 × 8k 上下文(MHA)= 2.0 GiB × 2 × 16 = 64 GiB——一张 24G 卡只剩哭的份,这就是 GQA 必须存在的定量证明;GQA 后 16 GiB,仍然紧,所以 vLLM 还有分页管理与 KV 量化兜底(2.8)。
部署检查习惯:任何方案先算一句”KV 预算 = 卡剩余显存 ÷ 单请求单 token KV”,再谈并发数。
8. 延伸资源
- nanoGPT repo + Karpathy《Let’s reproduce GPT-2 (124M)》——训练全流程实录
- GQA 论文(Ainslie et al. 2023)——十分钟读完
- FlashAttention 论文 §1–2——IO 感知的系统思维
2.4 预训练:数据、Scaling Law 与训练稳定性
本章目标:理解全量预训练在做什么、多少钱、为什么轮不到你做——以及你的机会在它上下游的哪里。学完标准:会算 6ND 的 FLOPs 账,能讲清 Chinchilla 定律和数据配比的逻辑,知道 loss spike 的标准处置。
1. 预训练在做什么:一个任务吃下全世界
训练目标极简:在数万亿 token 上做 next-token 预测(2.1)。工程量都在数据和稳定性上。
数据管线(现代 LLM 的真正护城河)
- 采集:Common Crawl 网页 + 代码(GitHub)+ 书籍 + 论文 + 多语种——代码数据占比高被证明能提升推理能力(即使纯中文对话任务也受益);
- 清洗:语言识别、广告/色情/毒性过滤、去重(精确去重 + MinHash 模糊去重——重复数据既浪费算力又造成记忆/过拟合)、质量打分(用小分类器学”维基百科 vs 随机网页”的差别);
- 配比:网页/代码/书/多语的混合比例是各家的核心 know-how,靠 scaling law 预测实验(在小模型上扫配比再外推);
- 课程:数据顺序有讲究(常把高质量数据放训练后期)。
认知:开源模型的差距,架构只占小头,数据和配比占大头——这正是卷5.2”数据为中心的 VLM”研究的产业背景。
2. Scaling Law:把”更大更好”变成预算表
- Kaplan 等(2020):test loss 对参数量 N、数据量 D、算力 C 呈光滑幂律,跨多个数量级成立。大模型的行为在小模型上可预测;
- Chinchilla(2022):修正配比——在固定训练算力下,参数和数据的等比缩放最优,经验值每参数约 20 token(GPT-3 时代模型普遍”欠喂”);
- LLaMA 路线的”故意过训”:Chinchilla 优化的是”训练算力最优”,但部署后推理成本才是终身大头——所以开源模型故意用远超 20:1 的数据量喂小参数模型(如 7B 喂 15T token),把智能压进小模型里,推理便宜。训练最优 ≠ 总成本最优,这是理解 2023 年后开源小模型井喷的钥匙。
对你的方法论启示:任何实验先在 1/10 规模验证趋势存在,再放大;反过来,读论文时看它的结论是否只在某一规模成立。
3. 训练稳定性:loss spike 的标准处置
长训必遇 loss 突跳(spike)。工业界的处置手册:
- 查数据:spike 常与某个坏 batch 相关(脏数据、超长序列)——跳过该 batch 往往自愈;
- 回滚:从 spike 前的 checkpoint 恢复,跳过问题数据段;
- 学习率手术:降 lr 重启 + 重新 warmup(把 optimizer 状态当作”受伤的关节”);
- 预防:grad clip 1.0(0.4)、QK-Norm、z-loss(防 logits 无界)、bf16。
通用超参配方(经验值速查):AdamW(0.9, 0.95)、wd 0.1 只 decay 2D 参数、grad clip 1.0、warmup 1~2%、cosine 到峰值 lr 的 10%。lr 峰值随模型变大而下调(0.1B→3e-4,1B→3e-4 级别,10B→1e-4 级别,量级感即可)。
4. 算力经济学:6ND 那笔账(必会)
训练 FLOPs ≈ 6ND(N 参数量,D token 数):前向每参数每 token 约 2 FLOPs,反向约 4。
算例:7B 模型喂 1T token:
一张 H100(bf16 有效算力按 40% 利用率 ≈ FLOPs/s)需要约 秒 ≈ 3.3 年。换成 512 张 H100:约 2.3 个月——这就是”预训练是巨头游戏”的定量含义(还没算租金:512 卡 × 2 个月 × 每卡时 1.5 美元 ≈ 55 万美元量级)。
你的位置在哪:预训练被垄断后,产业链的价值密度转移到了——后训练(SFT/RLHF,便宜 3 个数量级)、数据引擎、评测、领域微调、推理优化。2.10 章会把”学生的算力地图”画全;你现在只需要建立”任何实验先算 6ND”的条件反射。
5. 分布式一句话预告(7.3 详述)
单卡装不下时三招:数据并行(各卡完整模型、分数据)、张量并行(单层矩阵切开)、流水线并行(层切开接力),合称 3D 并行;配合 ZeRO/FSDP 把优化器状态/梯度/参数分片到各卡。概念先挂墙上,等你的实验真 OOM 了再回来(7.3)。
6. 开源可学的预训练项目(科研视角)
- nanoGPT:教学终点(2.3);
- TinyLlama / MobileLLM 系:小模型过训路线的公开实践;
- OLMo(AI2):数据、代码、中间 checkpoint、训练日志全开放——研究训练动态的最佳标本;
- Pythia:公开 154 个按序 checkpoint,研究”能力何时涌现”的常用资源。
7. 自测题
- 预训练数据管线的四步?哪一步最影响最终质量且最难复现?(采集/清洗/去重+过滤/配比;配比)
- Chinchilla 说了什么?LLaMA 为什么故意违反它?(每参数 20 token 等比;推理成本是终身大头,用数据换推理便宜)
- 6ND 里 6 是怎么来的?(前向 2 + 反向 4 FLOPs/参数/token)
- 13B 模型喂 100B token 大约多少 FLOPs?单张 4090(约 1e14 FLOPs/s 有效)要跑多久?(约 7.8e21;≈2.5 年——量级正确即可)
- spike 处置顺序?(查数据→跳过/回滚→lr 手术;预防靠 clip/norm/精度)
- weight decay 为什么跳过 1 维参数?(norm/bias 无方向性衰减意义,行规;也是读代码时的识别点)
8. 动手作业
- 写一个
estimate_training.py:输入参数量/token 数/GPU 型号,输出 FLOPs、单卡天数、N 卡月数和租金估算——以后每次立项先跑它; - 读 OLMo 的训练日志样例(repo 里有 wandb 记录),找到一次 loss spike,写 200 字分析;
- 用
datasets库下载一个小型中文语料(如 wikitext 或开源新闻集),实现 MinHash 去重原型,统计重复率——数据工程第一课。
9. 延伸资源
- Chinchilla 论文(Training Compute-Optimal LLMs)——必读,图表比公式多
- Kaplan scaling laws 论文——选读前半
- OLMo 博客与 repo——开放科学的样板
2.5 SFT 与指令微调实战
本章目标:把”会续写”的 base 模型变成”会回答”的助手——理解指令微调的原理、数据格式、loss mask,并用 LLaMA-Factory 跑通第一次真实微调。学完标准:能独立完成一次 SFT 并解释每个配置项在做什么。
1. 为什么 base 模型”不听话”
预训练模型是补全机:给它”中国的首都是”,它可能续写”一个国家的发展史……”(网页常见模式)。它不是不知道答案,而是没学过”问答”这种交互形式。SFT(Supervised Fine-Tuning)教的就是行为格式:把成千上万条”指令 → 高质量回答”喂给模型,让它进入”对话回答”的模式。
认知要点:知识几乎全部来自预训练,SFT 只是对齐格式、调出已有能力(这就是为什么 1000 条高质量数据也能显著改变行为——LIMA 论文的核心结论:“对齐可能是浅层的”)。反过来,SFT 也不能给模型注入它预训练时没见过的新知识——想让模型学领域知识,要么继续预训练,要么用 RAG。这个边界感是新手最常犯的认知错误。
2. 数据格式与 loss mask(本章最重要的技术细节)
一条指令数据的通用结构(Alpaca 风格):
{"instruction": "解释什么是过拟合", "input": "", "output": "过拟合是指模型……"}
多轮对话则用 role 结构(system/user/assistant)。训练时由 chat template 拼成最终文本:
<|im_start|>system
你是一个有用的助手。<|im_end|>
<|im_start|>user
解释什么是过拟合<|im_end|>
<|im_start|>assistant
过拟合是指模型……<|im_end|>
关键:loss mask。SFT 只在 assistant 回复的 token 上计算 loss,prompt 部分的标签置 −100(PyTorch 交叉熵的忽略值)。为什么:我们不想让模型”学着生成问题”,只想让它学回答。框架帮你做了,但你要知道它在哪——自己写 Trainer 或排查 loss 不降时,第一个查这里:
labels = input_ids.clone()
labels[:, :prompt_len] = -100 # prompt 不参与 loss
loss = F.cross_entropy(logits.view(-1, V), labels.view(-1), ignore_index=-100)
chat template 不一致是 SFT 的头号 bug:训练用什么模板,推理就必须用什么模板(包括 special token、换行、空格)。模板错位不会报错,只会让模型输出诡异——性能暴跌的第一嫌疑人。
3. 数据从哪来,质量与数量的关系
| 来源 | 特点 | 场景 |
|---|---|---|
| 人工标注 | 贵、质量最高 | 产品级模型 |
| 蒸馏强模型(现在主流) | 用 GPT-4o/Qwen-Max 生成回答 | 快速起步、领域数据 |
| 自指令(Self-Instruct) | 模型自举生成 | 老方法,质量一般 |
| 开源数据集 | Alpaca、ShareGPT 格式社区集合 | 练手 |
铁律:质量 > 数量。500 条覆盖面准、回答精的数据,胜过 5 万条平庸数据。蒸馏数据时最该花时间的是清洗:去重、长度过滤、答案质量再筛(可用强模型当裁判打分——“LLM-as-a-judge”,也是一套方法论)。领域微调(比如你未来的”美学 VLM”)的竞争壁垒就在这批数据上。
4. LLaMA-Factory 实战(寒假主线的工具)
LLaMA-Factory 是国内开源生态最常用的微调框架(同类:ModelScope SWIFT),整合了各模型的 template、LoRA、量化、评测:
- 安装:
git clone+pip install -e ".[torch,metrics]"; - 注册数据:把你的 json 放
data/,在data/dataset_info.json里登记(columns 映射 + tags 指定角色标签); - 写配置(yaml 一份,比命令行好维护):
model_name_or_path: Qwen/Qwen2.5-1.5B-Instruct # 练手先小模型
stage: sft
finetuning_type: lora
lora_target: all
lora_rank: 16
lora_alpha: 32
dataset: my_dataset
cutoff_len: 2048
learning_rate: 1.0e-4 # LoRA 的 lr,比全参大 10 倍(2.6 详述)
num_train_epochs: 3
per_device_train_batch_size: 2
gradient_accumulation_steps: 8
output_dir: saves/qwen-sft
- 训练:
llamafactory-cli train my.yaml; - 对话验证:
llamafactory-cli chat(必须用与训练一致的 template!)。
超参直觉:小数据(<5k)epoch 3,大数据 epoch 1~2;cutoff_len 够用就好(序列长度平方吃显存);LoRA 配置的完整讲解在 2.6。
5. SFT 的失败模式
- 复读机 / 多样性坍塌:epoch 太多或数据太少——模型背下了回答模板;
- 灾难性遗忘:模型忘了通用能力,只会你教的几十种句式——解法:混入通用数据(比如 1:1)、降 epoch、用 LoRA 而非全参;
- 模板错位:见 §2;
- 数据泄漏进验证集:评测虚高——去重后再切分。
6. 自测题
- SFT 能给模型注入新知识吗?为什么?(几乎不能;它改变行为分布,知识容量来自预训练——领域知识要靠继续预训练或 RAG)
- loss mask 为什么必要?忽略标签值是多少?(只学回答不学问题;−100)
- LIMA 的结论和它的边界?(1000 条高质量可对齐行为;但知识仍来自底座)
- 模板错位的症状和处理?(输出诡异不报错;逐字符比对训练/推理模板)
- 灾难性遗忘的两个解法?(混通用数据;LoRA 限制改动量)
- 为什么蒸馏数据的清洗比生成更花时间?(生成靠强模型,质量方差大:重复、幻觉、模板腔——不清洗就训进模型)
7. 动手作业(寒假里程碑第一段)
- 构造一个 500 条的垂直数据集(建议直接用强模型蒸馏:主题选你导师方向,比如”看画描述/流派判断/构图分析”——一鱼两吃);
- 用 LLaMA-Factory 对 Qwen2.5-1.5B 做 LoRA SFT,训练前后各截 10 个对比案例;
- 故意制造三个失败:epoch=10(复读机)、模板错位(输出诡异)、数据不清洗(质量差)——各写 100 字诊断,这是面试时最值钱的经验;
- 把数据构造脚本 + 配置 + 对比案例整理成 repo。
8. 延伸资源
- LIMA 论文(Zhou et al., 2023)——“对齐是浅层的”
- LLaMA-Factory 官方文档——照着走一遍 full pipeline
- Self-Instruct / Alpaca 论文——历史脉络
2.6 参数高效微调:LoRA 与 QLoRA
本章目标:彻底吃透 LoRA——你未来两年用得最多的训练技术。学完标准:能手写 LoRA 层,会算它的显存账,知道 rank/alpha/target_modules 怎么选,能用 QLoRA 在单张 24G 卡上微调 7B。
1. 显存对账:为什么需要 PEFT
0.2 章的公式:全参微调显存 ≈ 16 字节/参数(bf16 权重 2 + 梯度 2 + AdamW 状态 8 + fp32 主权重 4)。7B 模型全参 ≈ 112GB——单卡无解。
LoRA 的账:冻结权重(只存 2 字节/参数,bf16),训练的只有低秩增量(参数量 ~0.1–1%)。7B 模型:权重 14GB + 少量梯度和优化器状态 ≈ 24GB 卡能跑。这就是消费级卡微调时代开启的原因。
2. LoRA 原理(低秩假设的胜利)
核心假设(0.1 章 SVD 的直接应用):微调引起的权重变化 近似低秩——不需要动整个 矩阵,用两个瘦矩阵的乘积表达增量:
参数量从 降到 。例:4096×4096 的矩阵,r=16 → 从 16.8M 降到 131K(0.8%)。
初始化的讲究: 高斯初始化、 置零——保证训练起点 ,模型从预训练状态平滑出发(不破坏已学能力),这是”微调不该踢翻原解”哲学(0.1 章 §4.3)的架构化实现。
缩放系数 α:实际增量是 。α 固定(常取 2r),调 r 时学习率尺度自动稳定——你只需记配比 α = 2r。
3. 手写 LoRA 层(peft 的内核就这么多)
class LoRALinear(nn.Module):
def __init__(self, base: nn.Linear, r=16, alpha=32):
super().__init__()
self.base = base # 冻结的原层
for p in self.base.parameters(): p.requires_grad = False
self.A = nn.Parameter(torch.randn(r, base.in_features) * 0.01)
self.B = nn.Parameter(torch.zeros(base.out_features, r)) # B 置零!
self.scale = alpha / r
def forward(self, x):
return self.base(x) + self.scale * (x @ self.A.T @ self.B.T)
实战用 peft 库:
from peft import LoraConfig, get_peft_model
cfg = LoraConfig(r=16, lora_alpha=32, lora_dropout=0.05,
target_modules=["q_proj","k_proj","v_proj","o_proj","gate_proj","up_proj","down_proj"])
model = get_peft_model(model, cfg)
model.print_trainable_parameters() # trainable params: ~0.5% || 100%
选择指南:
target_modules:现代默认全挂(attention 四件套 + MLP 三件套)。早期只挂 q/v,实验证明 MLP 也很重要;- rank:数据少/任务简单 r=8–16;任务复杂/数据多 r=32–64;r 加大要配合数据量,否则过拟合更快;
- 学习率:LoRA 比全参大 10 倍左右(1e-4 ~ 2e-4)——只有增量在学习,敢迈大步。
4. QLoRA:4bit 底座上的 LoRA
LoRA 之后显存大头是冻结的权重本体(7B bf16 = 14GB)。QLoRA(2023)把它也压下去:
- NF4 量化:4bit 存储底座权重(NF4 是为正态分布权重定制的 4bit 数据类型,比均匀 int4 更贴分布);
- 反量化计算:前向时按需反量化到 bf16 做矩阵乘(存储 4bit,计算 bf16);
- 双重量化 + 分页优化器:量化常数本身再量化;显存峰值时优化器状态分页到内存——防 OOM 的保险。
结果:7B 模型 4bit 权重 ≈ 3.5GB + LoRA 参数与状态 + 激活 → 单张 24G 卡舒服微调,甚至 16G 卡能跑 7B。代价:训练速度慢 20–30%(反量化开销),精度损失实验上可忽略。LLaMA-Factory 里就是 quantization_bit: 4 一行配置。
5. 训练完之后:merge 还是留 adapter
- merge_and_unload():把 BA 乘积加回 W,得到独立模型——部署简单、推理零开销;但每个任务一个完整副本(7B bf16 = 14GB/个);
- 保留 adapter 文件(几十 MB):同一底座动态挂载多任务 adapter(多租户服务的做法);
- 上传 HF/ModelScope:LoRA 权重 + base 模型名 + 配置即可复现——寒假里程碑的交付形态。
常见坑清单:① 训练后忘 merge 或忘写 base model 名,加载直接报错;② dtype 混用(4bit 底座 + fp16 LoRA 会静默精度错乱,统一 bf16);③ target_modules 拼错名字静默不生效——print_trainable_parameters() 是 0 时及时发现;④ merge 时忘了 eval() 和dtype转换,输出乱码。
6. 其他 PEFT 一句话扫盲
Adapter(串联小瓶颈层,推理有额外延迟,已过气)|Prefix-tuning / P-tuning v2(在每层前加可学习软 token,全量推理开销,已边缘化)|DoRA(把权重分解为幅度+方向,方向上做 LoRA,小幅提升,可关注)。LoRA 家族是唯一的主流——理解它就理解了整个类别。
7. 自测题
- LoRA 的低秩假设是什么?为什么 B 初始化为零?(ΔW≈低秩;保证起点等于原模型)
- α/r 的作用?(学习率尺度的稳定器;α=2r 是惯例)
- 算账:Qwen2.5-7B(d=3584, 28 层)全挂 r=16 的 LoRA,可训练参数约多少?(7 个模块 × 2×16×(3584+3584)×28 ≈ 22M,约 0.3%——量级对即可)
- QLoRA 三件套?(NF4 量化底座 / bf16 反量化计算 / 双重量化+分页优化器)
- LoRA 学习率为什么比全参大 10 倍?(训练参数少一个数量级、B 起点为零——梯度小步长小,需放大)
- 多任务部署为什么留 adapter 不 merge?(几十 MB/任务 vs 14GB/任务;动态挂载)
- r 加大但不加数据的后果?(可训练容量↑ + 数据不变 → 过拟合加快;配合早停或降 r)
8. 动手作业(寒假里程碑第二段)
- 用第 3 节手写 LoRA 给一个预训练 ViT 的 attention 层加增量,在 CIFAR 微调,与全参微调对比精度和可训练参数量;
- LLaMA-Factory 用 QLoRA 微调 Qwen2.5-7B(租一张 4090):接续 2.5 的数据集,跑通 4bit 训练;
- 合并 adapter 并用 vLLM 起服务(2.8 预告,先跑通再说);
- 上传 HF/ModelScope:README 写清 base 模型、数据构造、训练配置、复现命令——这是你作品集的第一个大件;
- 实验记录:r=8/16/32 三档的验证 loss 曲线——亲手看到 rank 与过拟合的关系。
案例 · 数值:算清一次 LoRA 的参数账
案例:7B 模型全挂 r=16 的 LoRA,可训练参数是多少
LLaMA 式 7B:L=32,d=4096,每层挂 7 个线性层(q/k/v/o + gate/up/down),r=16。
每个模块: 参数。
全模型: 7B 的 0.42%。
训练状态(bf16 梯度 + fp32 AdamW 双动量):——对照全参微调约 70 GB 的梯度+优化器状态(7.1 的账),这就是 24G 卡能跑 7B 的完整解释。
验证手段:
model.print_trainable_parameters()应显示 ~29.4M / 0.42%——显示 0% 说明 target_modules 拼错了(7.2 案例群的经典静默失败)。
9. 延伸资源
- LoRA 论文(Hu et al., 2021)/ QLoRA 论文(Dettmers et al., 2023)——必读,各精读一遍
- peft 官方文档——API 速查
- Sebastian Raschka《LoRA 实操指南》博客系列——超参选择的工程视角
2.7 对齐技术:RLHF → DPO → GRPO
本章目标:搞懂”模型变聪明之后,如何变得有用/可靠”的三代技术。这一章是卷5.1(多模态推理 RL,当前最热方向)的理论地基——GRPO 就是你未来科研最可能亲手跑的算法。学完标准:能白板推导 DPO 的 loss,能讲清 GRPO 为什么去掉 critic 还能工作。
1. 什么是对齐,为什么难
SFT 之后的模型会回答了,但还有三层问题:回答质量的天花板(好答案 vs 更好答案,SFT 数据给不出稠密的区分)、幻觉(编造但自信)、目标偏差(讨好而非真实)。对齐(alignment)的本质:把人类模糊的”好坏”判断,变成模型可优化的信号。难点:人类偏好是相对的(比较容易、标定难——8.2 章美学评分同样的道理)且昂贵的。
2. 第一代:RLHF 三部曲(InstructGPT,2022)
- SFT:先教会行为格式(2.5);
- 训练奖励模型(RM):人类对同一 prompt 的多个回答做成对排序;RM 是个打分头,用 Bradley-Terry 模型拟合——“A 比 B 好”的概率 = ,本质是学习序关系而非绝对分( again,与 8.2 的 SRCC 逻辑同源);
- PPO 强化学习:模型生成回答 → RM 打分 → 按分更新策略。
KL 惩罚是这个阶段的灵魂设计:奖励里减去与参考模型(SFT 版)的 KL 散度——奖励模型会过优化(reward hacking:模型学会讨好 RM 的漏洞),KL 是”别漂太远”的缰绳:
PPO 的痛点:同时养四个模型(策略、价值网络、参考、奖励),采样-训练交替,超参敏感、训练不稳——工程上劝退了一票团队。于是第二代诞生。
3. 第二代:DPO(直接偏好优化,2023)
洞察:RLHF 目标有解析解——最优策略下的奖励可由当前模型与参考模型的概率比闭式表达:。把它代回 Bradley-Terry,奖励模型被整个消掉,得到直接监督学习式的 loss:
读法:让模型相对参考模型,把”好回答”的概率抬得比”坏回答”更高。两个模型(策略+参考,参考只做前向)、无采样、无 RL 训练循环——一次普通的前向反向就完成。
代价与局限:offline——只在给定偏好对上优化,模型不主动探索新回答,上限受数据覆盖限制;隐式奖励在分布外会失真。变体扫盲:IPO(修过拟合)、KTO(不成对,只要”好/坏”标签)、SimPO(去参考模型,用序列长度归一)。
4. 第三代:GRPO 与 RLVR(2024–2026 的主引擎)
动机来自”推理模型”时代:数学/代码题答案可自动验证(对答案、跑测试),不需要人类偏好标注,也不需要 RM——这就是 RLVR(可验证奖励的强化学习)。DeepSeek 用它练出 R1 的推理能力,引擎是 GRPO(Group Relative Policy Optimization)。
GRPO = PPO 去掉 critic 的简化:对每个问题,采样一组 G 个回答(比如 16 个),组内算分:
组内平均就是 baseline——“比我组内平均好的放大概率,差的缩小”。省掉价值网络(不用再训一个”预测期望得分”的模型),显存和稳定性双赢。配上 KL 到参考模型的约束,训练流程和 PPO 同构但简单得多。
为什么这是你科研的引擎:把”可验证”从数学/代码换到视觉领域——几何题的图、图表问答的数值、GUI agent 的任务完成——就是多模态推理 RL 的研究现场(卷5.1),且 GRPO 在 3B 模型上单卡可跑(TRL 的 GRPOTrainer / verl 框架)。当前这个方向论文的标配组件:Qwen-VL 小模型 + LoRA + GRPO + 自建可验证奖励,你在寒假后完全够格上手。
5. 三代对比(背下来)
| RLHF+PPO | DPO | GRPO/RLVR | |
|---|---|---|---|
| 模型数量 | 4(策略/价值/参考/奖励) | 2(策略/参考) | 2–3(策略/参考±奖励规则) |
| 奖励来源 | 训练出的 RM | 隐式(从偏好对反解) | 规则/验证器(零标注) |
| 数据 | 成对偏好 | 成对偏好 | 问题+可验证答案 |
| 稳定性 | 最难调 | 最稳(纯监督式) | 中等(组采样设计关键) |
| 典型用途 | 产品对齐 | 轻量偏好微调 | 推理能力训练 |
6. 实操路线(TRL)
- DPO 最短路径:
trl.DPOTrainer+ 成对数据(prompt/chosen/rejected三列 json),LoRA 底座,=0.1 起步,lr 比 SFT 再小一个档; - GRPO:
trl.GRPOTrainer,reward_funcs传一个 Python 函数(比如”最终答案与标准答案一致=1 否则=0”),G=8–16。奖励函数设计本身就是研究——写得太松会 reward hacking; - 数据:数学题用 GSM8K,验证用 str 匹配或小解析器。
7. 自测题
- RLHF 为什么要 KL 惩罚?去掉会怎样?(防奖励模型过优化/策略漂移;reward hacking 到崩)
- Bradley-Terry 模型把偏好建模成什么?和美学评分(8.2)的联系?(成对比较的 sigmoid 概率;都是”相对判断比绝对打分可靠”)
- DPO 的核心推导步骤?(RLHF 目标 → 最优策略下奖励的闭式解 → 代回消掉 RM)
- DPO 的 offline 局限是什么?(不探索新回答,上限受数据覆盖限制——对比 GRPO 的在线采样)
- GRPO 怎么省掉 critic?(组内采样的均值/方差即 baseline——同一问题的相对比较天然消去题难度)
- RLVR 的”可验证”指什么?举一个视觉领域的可能验证器?(规则自动判分;图表数值题比对数字、几何作图比对结论、GUI 任务完成状态)
- reward hacking 在 RLVR 里还发生吗?(发生:验证器松了就被钻空子——比如输出格式猜答案;验证器设计是研究活)
8. 动手作业
- 白板推导 DPO loss(从 KL 正则的 RL 目标出发,两步闭式代入)——推不动就对照原论文附录;
- TRL 跑一次 DPO:拿 2.5 的 SFT 模型当底座,构造 500 对偏好(好答案用强模型改写、坏答案故意注入错误),前后对比 20 个案例;
- 用 GRPOTrainer 在 GSM8K 子集上对 Qwen2.5-1.5B 做 RLVR(答案匹配奖励),观察训练中奖励均值曲线与回答长度曲线——R1 论文里”回答变长”现象的亲身体验;
- 读 DeepSeek-R1 论文前半部分(训练流程图级别),对照本章写一页总结。
案例 · 数值:代一次 DPO loss
案例:把公式里的符号全换成数字
。某样本的对数概率——策略模型:;参考模型:。
隐式奖励 = β ×(策略 − 参考): 好回答:;坏回答:。
margin → → 。
读出三件事:① 0.664 只比 (纯瞎猜)好一点——这个策略刚起步;② DPO 关心的唯一量是”相对参考模型的提升差”:把好回答的概率抬高、或把坏回答压低,都能拉开 margin;③ 永远不更新——它是整把尺子的零点,KL 缰绳以”对数概率差”的形式藏在公式里,而不是显式的惩罚项。
9. 延伸资源
- InstructGPT(RLHF 原始设定)/ DPO 论文——两篇必精读
- DeepSeek-R1 论文(2025)——GRPO+RLVR 的工业级叙事
- TRL 文档 DPOTrainer / GRPOTrainer 章节——实操手册
2.8 推理优化与 vLLM:把模型变成服务
本章目标:理解推理侧优化的全貌——量化、KV 压缩、批处理、投机解码——并把你的微调模型用 vLLM 部署成 OpenAI 兼容服务。学完标准:能算一张卡的并发容量,能跑一次量化前后对比实验,知道每项技术解决的是 2.3 章哪一种瓶颈。
1. 优化地图:瓶颈决定技术
2.3 章的结论是钥匙:prefill 是 compute-bound,decode 是 memory-bound。所有推理技术都在攻三个指标:显存(决定能否装下+并发)、吞吐(tokens/s 总量)、延迟(首个 token 时间 TTFT + 逐 token 间隔 TPOT)。对应关系:
| 技术 | 攻的瓶颈 | 一句话原理 |
|---|---|---|
| 权重量化 | 显存(权重本体) | 4bit 存权重,计算时反量化 |
| GQA / KV 量化 | 显存(KV cache) | 少存、省存 |
| PagedAttention | 显存碎片 → 并发 | OS 分页思想管理 KV |
| Continuous batching | 吞吐 | decode 的 memory-bound 让并发近乎免费 |
| 投机解码 | decode 延迟 | 小模型草稿、大模型并行验证 |
| CUDA Graph | decode 延迟 | 消除 kernel 启动开销 |
2. 量化:4bit 的数学直觉
线性量化的内核一句话:用缩放因子和零点把 fp16 的连续范围映射到 256 个整数档位:。精度损失来自档位间的舍入。工业方案三条路:
- GPTQ:训练后量化(PTQM),基于二阶信息(Hessian)逐列量化并补偿误差,权重紧凑、推理快——GPU 服务端主流;
- AWQ:激活感知——不是所有通道同等重要,按激活分布保护少量”关键权重”不量化/精细量化,实现简单效果好,出镜率高;
- bitsandbytes:运行时即时量化(QLoRA 的底座),易用性第一;
- GGUF / llama.cpp:CPU/端侧生态(Ollama 的底层),消费级硬件跑大模型的另一条路。
现实精度预期:8bit 几乎无损;4bit 掉 1–2%(多数任务无感,数学/代码类敏感);2bit 明显掉。量化是免费午餐但有保质期——你的评测必须在你自己的任务上重跑,不能信厂商数字。
3. PagedAttention 与 vLLM
传统 KV cache 管理:为每个请求预留连续最大长度显存 → 大量内部碎片 + 外部碎片,实际利用率常常不到一半。
PagedAttention(vLLM 的核心,2023):借鉴操作系统虚拟内存分页——KV cache 切成固定大小的 block(如 16 token/块),按需分配、逻辑连续物理分散。效果:显存利用率逼近满载,同样显存并发量翻数倍。
vLLM 的第二个杀手锏 continuous batching:静态 batching 等最慢请求结束才进下一批;continuous 版本每步动态增删请求——decode 阶段 memory-bound 的经济学(2.3 §4)被彻底兑现。
实操(寒假里程碑的最后一环):
pip install vllm
vllm serve Qwen/Qwen2.5-7B-Instruct \ # 或你 merge 后的本地模型路径
--max-model-len 8192 --gpu-memory-utilization 0.9
# 得到 OpenAI 兼容 API:http://127.0.0.1:8000/v1
from openai import OpenAI
client = OpenAI(base_url="http://127.0.0.1:8000/v1", api_key="none")
resp = client.chat.completions.create(
model="Qwen/Qwen2.5-7B-Instruct",
messages=[{"role": "user", "content": "用三句话解释 KV cache"}],
)
print(resp.usage) # prompt_tokens / completion_tokens——计费与容量的单位
你的微调模型从此获得”产品形态”:任何 OpenAI SDK 代码、任何前端(LobeChat 等)直接对接。
4. 投机解码:memory-bound 下的免费午餐
decode 逐 token 生成时 GPU 算力大量闲置。投机解码:小草稿模型(或大模型自己的小头)一口气猜 k 个 token → 大模型一次前向并行验证 k 个 → 接受最长的正确前缀。接受率高的领域(代码、模板化文本)加速 2–3 倍,输出分布数学上等价于大模型单独生成——加速不改变质量,这是它优于”直接用小模型”的关键。vLLM 里 --speculative-model 一行开启。延伸:自投机版本(Medusa/MTP 多预测头)是多 token 预测路线的起点,前沿在继续演化。
5. 并发容量的算账方法(部署前必做)
一张卡的容量账,三步:
- 权重:7B bf16 = 14GB(或 4bit ≈ 3.5GB);
- KV cache 预算:剩余显存 ÷ 单请求单 token KV(2.3 §3 的公式)= 可容纳的总 token 数;例:4090 上 7B bf16(24GB,留 2GB 余量)→ KV 预算 8GB → 单请求 4k 上下文约 500 个并发槽(GQA 后更多);
- 实际并发 = min(显存槽位, 算力能跟上的 batch) ——decode 时 batch 大到一定程度后 TPOT 开始恶化,压测找拐点。
吞吐指标速记:单请求 decode 速度 ≈ 显存带宽 ÷ 模型字节数(7B bf16 ≈ 14GB / 1000GB/s ≈ 70 tokens/s 理论上限,实测 40–60)。这个公式让你不看任何宣传就能估”这张卡跑这个模型多快”。
6. 自测题
- 为什么 4bit 量化”大多无感”而 2bit 明显掉?(档位数对信息保真的非线性;权重大部分冗余、少数关键——AWQ 的洞察)
- PagedAttention 解决什么?类比什么系统?(KV 显存碎片;OS 虚拟内存分页)
- continuous batching 比静态 batching 强在哪?(不等最慢请求,每步动态增删——兑现 memory-bound 的并发经济学)
- 投机解码为什么不损害输出质量?(拒绝采样保证分布等价;只是用并行验证替代串行生成)
- 单请求 decode 速度的估算公式?(带宽÷权重字节数;算出 7B bf16 在 4090 上 ≈ 50–70 tok/s)
- 部署你 merge 后的 7B,4090 上第一个该调的参数是什么?(—gpu-memory-utilization 和 —max-model-len——KV 预算的两个把手)
7. 动手作业
- vLLM 部署 2.6 的微调模型(LoRA 也可直接挂载:
--enable-lora),用 OpenAI SDK 调通; - 压测:写 50 行脚本(asyncio + 50 并发),测吞吐/TTFT/TPOT 随并发数的变化,找出你这张卡的拐点;
- 量化对比:同一模型 fp16 vs GPTQ-4bit(或 AWQ),在你 2.5 构造的评测集上对比质量、速度、显存三件套,出一张表;
- 挑战:开投机解码对比延迟;或用
llama.cpp把 4bit 模型跑到你的 CPU 上,体验端侧路线。
8. 延伸资源
- vLLM 官方文档(quickstart + 性能调优页)
- PagedAttention 论文(Efficient Memory Management for LLM Serving)——十分钟
- AWQ / GPTQ 论文——按需精读
- SGLang——另一主流引擎(RadixAttention 前缀缓存是亮点),vLLM 学扎实后对照看
2.9 架构前沿:MoE、长上下文与注意力变体
本章目标:建立”前沿架构”的坐标系——不追求跟每个新模型,而是看懂它们都在解哪两道题:算力不够怎么装下更多参数(MoE)和上下文怎么无限长(长上下文)。学完标准:能向别人解释 DeepSeek-V3 的 671B/37B 是什么意思,以及 128k 上下文靠什么技术撑起来。
1. MoE:参数与算力的解耦
问题:dense 模型每生成一个 token 都要激活全部参数——100B 模型每 token 就是 100B 的计算。 scaling law 说参数越多越好,算力账说算不动。
MoE(Mixture of Experts)的解法:把每层的 FFN 换成 N 个”专家”FFN + 一个 router。每个 token 只被路由到 top-k(常为 8 选 1 或 16 选 2)个专家处理:
结果:总参数量与每 token 激活量分离——DeepSeek-V3:总参 671B,每 token 只激活 37B。训练时用大参数容量学知识,推理时只付激活量的算力钱。这就是”算力不够,参数来凑”的产业答案,2024 年后开源旗舰几乎全是 MoE(DeepSeek、Qwen3 旗舰、GLM 旗舰)。
工程代价(概念级了解):负载不均(专家冷热不均 → 加 auxiliary balance loss 强制均衡);训练时专家分布在不同卡上,all-to-all 通信成为系统瓶颈(这是 MoE 训练框架的护城河);小模型上 MoE 常不划算(路由开销占比大)——MoE 是规模的武器,不是学生的。
2. 长上下文:三道子问题
把上下文从 4k 拉到 128k+,要同时解决:
- 位置编码的外推:训练只见过 4k 位置,推理给 128k 位置,RoPE 直接崩。解法家族:位置插值(PI)——把位置索引除以系数塞回训练范围;NTK-aware / YaRN——更聪明的”按频率分层缩放”(高频转得慢保局部、低频动得多扩全局),微调少量长文本即可扩展数倍。只需要记住结论:现代模型的长上下文 = RoPE + YaRN 类缩放 + 少量长文本继续训练;
- 注意力的平方成本:prefill 和 KV cache 都随长度平方/线性暴涨。工程解法(2.3/2.8 已铺垫):FlashAttention 系列(IO 优化不降复杂度)、稀疏/滑窗注意力(局部+少量全局锚点)、KV 压缩(选择性丢弃/合并历史 token);
- 数据里长文档稀缺:预训练语料长文占比低,需要专门的长文本数据阶段 + “大海捞针”(needle-in-a-haystack)评测——在长文里埋一句”暗号”考检索,是长上下文的标配考卷。
RAG 与长上下文的分工(常被问):长上下文不是 RAG 的终结——检索便宜且精准,塞 128k 文档既贵又”中间失明”(模型对长上下文中部信息利用率低)。现实产品:先检索压缩、再给模型精料。
3. 注意力变体速览(知道名字与动机即可)
- MLA(Multi-head Latent Attention,DeepSeek):把 KV 压到低秩潜空间存储,KV cache 压缩数倍——与 GQA 同一目标的不同路线;
- 线性注意力 / RWKV / Mamba(状态空间模型):把”看全部历史”改成”维护固定大小状态”,复杂度 O(N)、KV 恒定。纯替代方案在与 Transformer 的正面比拼中互有胜负,但混合架构(少数注意力层 + 多数线性层,如 Jamba)是落地形态——“注意力的精确检索 + 线性层的廉价记忆”各取所长;
- 滑动窗口 + 全局锚点(Gemma 等在用):多数层看局部窗口,少数层看全局——用 5% 的成本拿到 95% 的效果。
读前沿的方法论:每出一个新架构,先问三个问题——它把哪个量降下来了(参数/激活/KV/复杂度)?代价是什么(质量/工程/灵活性)?在什么规模下划算?——比记结构图有用。
4. 自测题
- MoE 的核心解耦是什么?671B/37B 什么意思?(总参数与每 token 激活量;总参 671B、每 token 只算 37B)
- 为什么 MoE 需要负载均衡 loss?(router 惰性扎堆热门专家——不均衡则大参数白养)
- YaRN 类缩放解决什么?(RoPE 位置超出训练范围的外推——按频率分层缩放旋转角)
- 长上下文三道子问题分别是什么?(外推 / 平方成本 / 长数据稀缺)
- “大海捞针”考什么?它测不测推理?(长文检索保真;不测多跳推理——所以还要别的考卷)
- RAG 为什么没被长上下文杀死?(成本、中部失明、检索精度;两者是分工不是替代)
- 线性注意力换来了什么、付出了什么?(O(N) 和恒定状态;牺牲全局精确检索——所以混合架构落地)
5. 动手作业
- 用 vLLM/transformers 对同一个 4B 模型测 1k / 8k / 32k 输入的 prefill 耗时,画曲线——亲眼看平方项;
- 跑一次大海捞针开源评测(很多 repo 可一键),对一个开源 4B 模型测 4k/16k/32k 的命中率曲线;
- 算账:Qwen3-30B-A3B(30B 总参/3B 激活)对比 Qwen3-32B dense,每 token 计算量差多少倍?这对部署意味着什么?
- 挑战:读 YaRN 论文 §1–2,用三句话讲清”高频少动、低频多动”为什么合理。
6. 延伸资源
- YaRN 论文(RoPE 缩放的集大成)
- DeepSeek-V3 技术报告 §1–2——MoE + MLA 的工业叙事
- Mamba 论文 §1——状态空间视角,看个动机即可
2.10 小模型时代的科研机会:1B–7B 甜点区
本章目标:把”算力有限”从劣势翻译成研究议程——为什么小模型不只是”缩水版”,而是独立的研究对象;给出学生的算力阶梯和选题映射。学完标准:能对任何”我想研究 X”回答”用多大的模型、什么卡、多少卡时、预算几块钱”。
1. 为什么小模型是正经研究对象
三条产业事实撑起这个判断:
- “过训小模型”是开源主流路线(2.4 §2):LLaMA/Qwen 的 1.5B–7B 都用远超 Chinchilla 配比的数据喂养——“把智能压进小模型”本身是开放问题:多少数据、什么配比、什么课程能把 1.5B 推到极限?没有标准答案;
- 端侧与降本的真实需求:手机、车机、本地部署都要 1–4B 模型;API 厂商也要小模型扛住高并发低成本层。小模型的每 1% 提升都有直接定价意义;
- 科研范式友好:R1 的 distilled 系列证明小模型吃推理蒸馏成长极快;GRPO 在 1.5B–3B 上单卡可跑——当前最热的研究循环(RLVR)恰好发生在你能负担的规模。
科学问题层面,小模型上的问题一样深刻:能力涌现的机制、蒸馏中什么保留了什么丢了、数据效率的上界、量化的领域敏感性——问题的价值不随模型大小缩水。
2. 学生的算力阶梯(2026 价格)
| 档位 | 资源 | 能做什么 |
|---|---|---|
| 0 元 | Kaggle(周 30h)/ ModelScope 免费卡 / Colab | Qwen2.5-1.5B LoRA SFT;1B GRPO 小实验;全部卷0–卷2 作业 |
| ~2 元/小时 | AutoDL/仙宫云 4090 24G | 7B QLoRA SFT/DPO(寒假里程碑);2–4B VLM LoRA 微调;3B GRPO(LoRA) |
| ~5–8 元/小时 | A100 80G / 多卡 4090 | 7B 全参 LoRA 大 rank;多模态 RL 批量实验;评测流水线 |
| 组内/云集群 | 导师资源(谈下来的) | 继续预训练 1–4B(域内 10B token 级);大模型推理评测 |
决策公式:立项前先写三行——模型多大?卡是什么?预计卡时×单价=?超预算就降级模型或缩数据,永不放弃问题本身。例:多模态 RL 论文复现 → 原 paper 用 7B×8 卡,你换成 Qwen3-VL-2B + LoRA + 单 4090,验证同样的科学假设——这叫等比缩放实验设计,是学生科研的标准姿势(审稿人也认:在小模型上干净的证据 > 大模型上蹭的实验)。
3. 甜点区选题地图(每条都标了算力档)
- 垂直领域小 VLM(0 元起):Qwen3-VL-2B + LoRA + 你造的数据(2.5 的方法论搬到多模态)——美学/艺术方向正好对接卷8;
- 小模型 RLVR(4090):GRPO + 可验证奖励(2.7 §4 的 TRL 流程搬到 1.5B)——多模态验证器设计是论文级问题(卷5.1);
- 蒸馏研究(4090–A100):大模型什么能力蒸馏得进 1.5B?什么必然丢失?——便宜且深刻;
- 数据为中心(0 元–4090):固定 1.5B 固定预算,只动数据配比/质量/课程——控制变量干净的实验设计训练场(卷5.2);
- 评测与基准(0 元):领域基准(如”VLM 看画”评测集)——算力几乎零,学术杠杆最高,也是进组最快的敲门砖;
- 量化的领域敏感性(0 元–4090):4bit 量化在哪些任务上塌、为什么——产业真问题,实验便宜。
4. 寒假里程碑的完整算力预算(对齐 9.1 执行计划)
nanoGPT 练手(0 元,Kaggle)→ 1.5B LoRA SFT(0 元,免费卡)→ 7B QLoRA + DPO(4090 约 8–12 小时 ≈ 20 元)→ vLLM 部署 + 评测(本地/免费)→ 上传 HF。整个寒假的 GPU 开销一杯奶茶钱——算过账之后,“没算力”永远不再是借口。
5. 自测题
- “过训小模型”为什么是开放问题而不是工程细节?(数据配比/课程对极限的影响无标准答案——每家 know-how)
- 等比缩放实验设计的要点?(换更小模型/更短训练,但保持科学假设与控制变量不变;先小后大验证趋势)
- 你的预算三行公式是什么?(模型大小 / 卡型 / 卡时×单价)
- 为什么评测类选题学术杠杆高、适合敲门?(零算力、公开可比、影响后续所有工作;也是快速熟悉领域的路径)
- GRPO 为什么恰好落在学生算力区?(组采样可小 G、LoRA 可训、验证器零训练成本——三个因素都缩在 1.5–3B 甜点)
6. 动手作业(本卷收官作业)
- 把你想做的第一个研究想法写成一页纸 proposal:问题、假设、模型/卡型/预算三行、评测方案、风险与降级路径——找导师面谈时带着它;
- 建”实验台账”(一个 csv 或 notion):日期/实验名/配置/结果/结论一行制——从第一次实验就养成习惯;
- 卷2 收官自查:不翻笔记,向同学讲清”一个 7B 从预训练到上线服务”的全链路(数据→预训练→SFT→DPO/GRPO→量化→vLLM)。讲不顺的章节回去重读。
7. 延伸资源
- SmolLM 系列博客(HuggingFace)——“从零造小模型”的完整公开记录
- DeepSeek-R1 蒸馏章节——小模型吃推理能力的实证
- LLaMA / Qwen 技术报告的”训练配方”小节——工业界如何回答第 1 节的问题
3.1 多模态总览:把视觉接进语言模型的三条路线
本章目标:建立多模态领域的顶层地图。所有 VLM 论文(包括你将来要读的每一篇)都在回答同一个问题——视觉信息以什么形式、在哪个位置进入语言模型。学完标准:拿到任何新 VLM,能在 5 分钟内判断它属于哪条路线、connector 是什么、视觉 token 有多少。
1. 核心矛盾:两个模态说着不同的语言
LLM 的世界是离散 token + 词表 + 下一 token 预测(卷2);视觉塔(ViT/CLIP)输出的是连续特征向量,维度、尺度、语义结构都和词嵌入空间完全不同。多模态的全部工程与科研,本质都是解这道”接口题”。三条路线对应三种哲学:
2. 路线一:双塔对齐(CLIP 范式)——“各说各话,但对得上”
两个独立编码器,各自把图像/文本编码进共享嵌入空间,用内积对齐(1.5/1.6 已实操)。
- 能干什么:检索(以文搜图)、zero-shot 分类、打分(8.2 的美学/奖励模型底座)、数据过滤;
- 干不了什么:没有生成——它只会”匹配”,不会”回答”。你问它”图里的人在做什么”,它给不了自回归的文本;
- 定位:对齐空间的提供者。它虽然不是 VLM 本体,却是所有 VLM 的零件供应商(视觉塔几乎都从 CLIP/SigLIP 初始化)。
3. 路线二:桥接(Connector 范式)——“视觉是外语,翻译给 LLM 听”
当前理解类 VLM 的绝对主流:冻结(或微调)的视觉塔 + 一个轻量 connector + LLM。视觉特征经 connector 投影成”视觉 token”,像外语单词一样插进文本 token 序列,之后 LLM 用同一套注意力统一处理:
输入序列: [文本 token...] [视觉 token ×576] [文本 token...] → LLM → 文本回答
这个心智模型请焊死:视觉 token 就是嵌入空间里的”外来词”。由此立刻推出三件事——① LLM 不需要改架构(还是卷2 那个 GPT);② 序列长度=文本+视觉 token,注意力平方的账照算(1.4 的核心矛盾);③ 训练目标没变,还是 next-token prediction——VLM 的训练在形式上就是 SFT,只是输入里混了视觉 token。
代表:LLaVA(3.2 详拆)、BLIP-2、Flamingo、Qwen-VL 系列、InternVL(3.3 横评)。
4. 路线三:原生融合(Native/Early-fusion)——“从胎教开始学双语”
不做”接口”,从预训练第一天就把图文混在一起训练:图像经视觉 tokenizer 或 patch 化变成 token,与文本 token 进同一个词表/同一套 Transformer,统一 next-token 训练。
- 代表:Fuyu(patch 直接进 decoder,连视觉塔都省了)、Chameleon/Emu3(离散 VQ token,卷4.8)、Qwen3-VL 的 early-fusion 训练(视觉 token 从头参与预训练——2026 年头部模型明确转向此路线,不再”先学语言后补视觉”);
- 优势:模态间深度融合(不是拼接层面的理解)、架构最干净、天然通向理解+生成统一;
- 代价:预训练成本全价,只有巨头玩得起——但它的技术报告是学生最好的读物(见 3.5)。
5. 三条路线对比(背下来)
| 双塔对齐 | 桥接 | 原生融合 | |
|---|---|---|---|
| 视觉进入位置 | 不进 LM | 嵌入序列拼接 | 同一词表从头混训 |
| 代表 | CLIP/SigLIP | LLaVA/BLIP-2/Qwen-VL | Fuyu/Chameleon/Qwen3-VL(趋势) |
| 能力 | 检索/打分 | 理解+对话+推理 | 理解+生成(潜力) |
| 训练成本 | 低 | 中(借 LLM 东风) | 最高 |
| 产业角色 | 零件/基础设施 | 当前 VLM 主力 | 下一代方向 |
演化主线一句话:融合点不断提前——从”用完再对齐”(双塔)到”进 LM 时拼接”(桥接)到”预训练时就同班同学”(原生)。你论文的 innovation 也大概率落在”融合点/融合方式”这个轴上。
6. 判断框架:拿到新 VLM 先问四个问题
- 视觉塔是什么(CLIP/SigLIP/自研)?冻不冻?
- connector 是什么(线性/MLP/resampler/Q-Former)?压到多少视觉 token?
- 训练分几阶段?各阶段冻什么训什么?(3.2 用 LLaVA 给出标准答案)
- 数据是什么(caption 预训练 + 指令数据配比)?
四问的答案就是这篇论文的”配置清单”——90% 的 VLM 论文差异都在这四项里,也直接对应你的复现计划。
7. 自测题
- 双塔为什么不能”回答问题”?(无自回归解码器,只学了对齐空间)
- “视觉 token 是外语”推出哪三个工程结论?(LLM 架构不变 / 序列变长平方成本 / 训练目标仍是 next-token)
- 原生融合比桥接好在哪、贵在哪?(深度融合与统一潜力;全价预训练)
- 视觉 token 数量为什么是核心矛盾?(576 个起,高分辨率/视频爆炸,注意力平方)
- CLIP 既然不是 VLM,为什么仍是产业地基?(视觉塔初始化、数据过滤、奖励模型、检索——四位一体)
8. 动手作业
- 画一张三路线对比图(手画或 PPT),每个路线标一个代表模型和你自己的例子;
- 挑一篇你感兴趣的 VLM 论文(建议 LLaVA-1.5 或 Qwen2-VL 报告),用 §6 四问列它的”配置清单”——3.2 复现 LLaVA 前的预习;
- 算账:CLIP ViT-L/14 在 336px 下产生多少视觉 token?(336/14=24 → 576+1 CLS;再算 896px 下 anyres 切块后的数量级)
图解 · 三条路线一张图
flowchart TB
IN["图像 + 文本"] --> R1["路线一:双塔对齐<br>CLIP / SigLIP<br>各自编码 → 共享空间"]
IN --> R2["路线二:桥接<br>视觉塔 + connector + LLM<br>视觉 token 塞进序列"]
IN --> R3["路线三:原生融合<br>同一词表 / 从头混训<br>early-fusion"]
R1 --> O1["产出:检索 / 打分 / 过滤<br>(不能生成)"]
R2 --> O2["产出:理解 + 对话 + 推理<br>(当前主力)"]
R3 --> O3["产出:理解 + 生成统一<br>(下一代方向)"]
O1 -. "零件供应商:视觉塔 / 数据过滤 / 奖励底座" .-> R2虚线是常被忽略的关系:双塔不是路线二的对手,而是它的上游供应商——CLIP 提供视觉塔初始化、训练数据过滤、奖励模型底座(8.2/4.4)。三条路线是产业链分工,不是三个孤岛。
9. 延伸资源
- LLaVA-1.5 论文(Improved Baselines with Visual Instruction Tuning)——下一章主角,先读
- “Multimodal Foundation Models: From Specialists to General-Purpose Assistants”(Li et al. 综述)——地图级读物,选读
- Qwen3-VL 技术报告——early-fusion 的一手材料
3.2 LLaVA 范式精读与复现:两阶段训练全流程
本章目标:吃透 LLaVA——结构最简、血统最正、最适合复现的 VLM 骨架。几乎所有开源 VLM 都是它的变体。学完标准:能讲清两阶段各自冻什么训什么、为什么这样设计,并能亲手跑一次迷你版两阶段训练。
1. 架构:简单到令人不安
LLaVA-1.5 的全部组件:
- 视觉塔:CLIP ViT-L/14 @336px → 576 个视觉特征(336/14=24,24×24=576,取 patch token,CLS 弃用);
- Connector:一个两层 MLP(
Linear(1024→d) → GELU → Linear(d→d))——把 CLIP 特征投影到 LLM 词嵌入空间; - LLM:Vicuna/Qwen(任意 decoder-only)。
设计哲学:把复杂度从架构转移到数据和训练。后来者不断证明”简单 connector + 好数据 > 复杂 connector”(3.3 的 Q-Former 之死),这是本领域最重要的经验教训之一。
2. 输入怎么拼:inputs_embeds 拼接(复现的核心技巧)
占位符方案:文本里写 <image> 占位 token(占 576 个位置),过 embedding 层后,把这几个位置的嵌入向量替换成 projector 输出的视觉特征,再喂给 LLM:
embeds = llm.get_input_embeddings()(input_ids) # (B, L, d) 文本嵌入
img_feats = proj(vision_tower(pixel_values)) # (B, 576, d) 视觉特征
embeds[img_mask] = img_feats.flatten(0, 1) # 占位位置替换
out = llm(inputs_embeds=embeds, attention_mask=mask) # 一套注意力统一处理
之后的一切(causal mask、next-token loss、SFT 的 loss mask)与卷2 完全相同。没有新机制——这就是 LLaVA 的力量所在。
3. 两阶段训练(必考,也是你复现的目录)
阶段一:特征对齐(pretrain projector)
- 冻结:视觉塔 ❄️ + LLM ❄️;训练:仅 projector(约几十 M 参数);
- 数据:约 558K 图文 caption(原版用 LCS558K,你复现用小规模 caption 集);
- 为什么这样设计:CLIP 特征是”检索友好”的,但 LLM 词嵌入空间不认识它。此阶段的唯一任务是让 projector 学会翻译——把视觉特征平移到 LLM 嵌入空间中”有意义的位置”。LLM 冻结保证了翻译目标稳定(空间不动,只学映射)。
阶段二:视觉指令微调(SFT)
- 冻结:视觉塔 ❄️(原版);训练:projector + LLM 全开;
- 数据:665K 指令数据(多轮对话、VQA、详细描述、推理题,用 GPT-4 从 caption/框标注合成的”学术任务数据”——又是数据为中心的胜利);
- 为什么 LLM 要解冻:模型要学会使用视觉信息回答问题(视觉条件下的语言能力),这是行为层的学习,需要整个 LLM 参与。
之后的演化(知道即可)
LLaVA-NeXT(AnyRes):高分辨率图切成网格块分别过 ViT + 一张缩略图——动态分辨率的标准解法,Qwen-VL 的动态 patch 同属此思路的家族;LLaVA-OneVision:图文视频统一训练。你复现的迷你版做到阶段二即可称为完整 LLaVA。
4. 迷你复现路线(学生算力版,大三下的第一个大项目)
配置:视觉塔用 open_clip 的 ViT-B/16(冻结);LLM 用 Qwen2.5-0.5B-Instruct(0 元档友好);projector 两层 MLP。
阶段一(免费卡可跑):
- 数据:COCO caption 子集 5–10 万条(HF
HuggingFaceM4/COCO或本地裁剪); - 训练:仅 projector,bs 尽量大、epoch 1、lr 1e-3(新模块学习率可以大);
- 验收标准:让模型对没见过的图做 caption,输出应”像话”——如果胡言乱语,对齐没成。
阶段二(租 4090 数小时):
- 数据:LLaVA-Instruct 的一个子集(1–3 万条)或自己蒸馏的领域指令数据(接你导师方向);
- 训练:projector + LLM(LoRA 或全参,0.5B 全参单卡毫无压力),lr 2e-5(LoRA 则 1e-4),epoch 1–2;
- 验收标准:VQA 问答合理、能指图说话(grounding 描述)、无严重幻觉。
数据格式注意:<image>\n{question} 里占位符 expansion 由框架处理——用 LLaMA-Factory 时它的 llava template 已封装(visual_inputs 传图);用 transformers 的 AutoProcessor 系(Qwen2-VL 类)则走 apply_chat_template + image_token。第一次跑通建议直接用 LLaMA-Factory 的多模态配置,第二次再用裸 transformers 自己拼 inputs_embeds——前者学工程,后者学原理,两个都要做。
5. 失败模式速查(复现时的排障表)
| 症状 | 嫌疑人 |
|---|---|
| 阶段一后 caption 全是重复短语 | projector 学习率过大 / 数据太少 / LLM 没冻结住(意外被更新) |
| 阶段二后”失明”(回答与图无关) | 视觉特征没替换进正确位置(占位符 mask bug)/ projector 输出 dtype 错 |
| 图像越精细回答越差 | 分辨率处理不一致(训练 336 推理 224 之类)——预处理必须逐位一致 |
| loss 正常但回答是英文模板腔 | 指令数据语言分布 / LLM 底座太小 |
| 显存爆 | 视觉 token 数 × 序列长——max_seq_len 和图片分辨率先降一档 |
6. 自测题
- 阶段一为什么冻结 LLM?阶段二为什么解冻?(对齐目标稳定 / 学习视觉条件下的行为)
- 576 个视觉 token 从哪来?(336px ÷ 14px patch → 24×24)
- 为什么 CLIP 特征不能直接当词嵌入用?(检索空间 ≠ 词嵌入空间,尺度与语义结构不匹配——projector 是翻译官)
- AnyRes 解决什么?(高分辨率:切块保留细节 + 缩略图保全局)
- LLaVA 的经验教训对科研选择有什么启示?(数据与训练质量 > 架构炫技——“简单基线调强”是顶会认可的路径)
7. 动手作业(大三下里程碑第一段)
- 完成迷你版两阶段训练,repo 里放:训练前(阶段0:未对齐)→ 阶段一 → 阶段二 的同一批图片的回答对比图——这个对比是你理解”对齐”的最好证据,也是面试杀手锏;
- 消融一个变量(选一):阶段一数据量减到 1 万看对齐质量退化;或把 MLP projector 换成单层 Linear 对比;或解冻视觉塔观察是否过拟合;
- 用你的模型跑 8.1 作业里挑的名画——写下它”看画”时的具体错误,这是卷8.5(VLM 看画)的第一手素材;
- 训练日志 + 显存曲线进 README(用 0.4 的四件套)。
图解与案例 · 两阶段管线与”一条样本的一生”
flowchart LR
subgraph S1["阶段一:对齐(只训 projector)"]
I["图像"] --> V["视觉塔 ❄️"] --> P["projector 🔥"] --> M1["caption loss"]
M2["55.8万 caption"] --> M1
end
P --> OUT1["学到了:翻译能力"]
subgraph S2["阶段二:视觉指令微调(projector + LLM 解冻)"]
OUT1 --> D2["指令数据"] --> T2["projector 🔥 + LLM 🔥<br>视觉塔仍 ❄️"]
end
T2 --> OUT2["学到了:看图说话的行为"]案例:一条训练样本的一生
输入:一张 336×336 油画 + 问句”这幅画的流派是什么?”
- 图像过冻结 CLIP → 576 个特征 → projector → 576 个”外语 token”;
- 问句 tokenizer 后约 12 个文本 token;序列中
<image>占位符所在的 576 个位置被视觉嵌入顶替;- 最终序列:
[视觉×576][问句×12][回答×8],整条过一次 causal attention——视觉 token 对 LLM 就是不认识但可以学的外来词;- loss mask:问句部分标签 = −100(不学提问),只有回答的约 8 个 token 计入 loss;
- 阶段一时 LLM 冻结 → 8 个 token 的梯度只流向 projector(学翻译);阶段二解冻 → 梯度涌向整个 LLM(学行为)。
一段话总结:VLM 训练没有新机制,只是”把一批特殊 token 塞进序列 + 规定哪些位置算 loss”。
8. 延伸资源
- LLaVA 原论文 + LLaVA-1.5 论文——连读,看”简单架构如何一步步调强”
- llava 官方 repo(
LLaVA-VL)——llava/train/train.py对照本章逐行读 - LLaMA-Factory 多模态文档——工程捷径
附录 · 完整可运行脚本:llava_mini.py(教学骨架)
依赖:
torch>=2.2 transformers>=4.44 open_clip_torch pillow tqdm。数据:jsonl,每行{"image": "path.jpg", "question": "...", "answer": "..."}。这是教学骨架(跳过 chat template,模板问题见 2.5)——先跑通,再换成 LLaMA-Factory 正式管线。
# llava_mini.py —— 迷你 LLaVA:视觉塔❄️ + projector + Qwen2.5-0.5B
import argparse, json, math, torch, torch.nn as nn
from PIL import Image
from torch.utils.data import Dataset, DataLoader
from transformers import AutoModelForCausalLM, AutoTokenizer
import open_clip
class MiniLLaVA(nn.Module):
def __init__(self, device="cuda"):
super().__init__()
self.clip, _, _ = open_clip.create_model_and_transforms("ViT-B-16", pretrained="openai")
self.clip = self.clip.to(device).eval()
for p in self.clip.parameters(): p.requires_grad = False # 视觉塔永久冻结
d_llm = AutoModelForCausalLM.from_config(
__import__("transformers").AutoConfig.from_pretrained("Qwen/Qwen2.5-0.5B-Instruct")).config.hidden_size
self.proj = nn.Sequential(nn.Linear(512, d_llm), nn.GELU(), nn.Linear(d_llm, d_llm))
self.llm = AutoModelForCausalLM.from_pretrained(
"Qwen/Qwen2.5-0.5B-Instruct", torch_dtype=torch.bfloat16).to(device)
self.tok = AutoTokenizer.from_pretrained("Qwen/Qwen2.5-0.5B-Instruct")
self.device = device
def vision_tokens(self, pixel): # (B,3,224,224) → 49 个 token
f = self.clip.encode_image(pixel, normalize=False) # (B,512,7,7) 前置投影后
return f.flatten(2).transpose(1, 2) # (B,49,512)
def forward(self, pixel, q_ids, a_ids):
vis = self.proj(self.vision_tokens(pixel).to(torch.bfloat16)) # (B,49,d)
qe = self.llm.get_input_embeddings()(q_ids) # (B,Lq,d)
ae = self.llm.get_input_embeddings()(a_ids) # (B,La,d)
inputs = torch.cat([vis, qe, ae], dim=1)
Lq, La = q_ids.size(1), a_ids.size(1)
labels = torch.cat([torch.full((inputs.size(0), 49 + Lq), -100,
device=inputs.device, dtype=torch.long), a_ids], dim=1)
return self.llm(inputs_embeds=inputs, labels=labels) # HF 内部算 shift loss
class DS(Dataset):
def __init__(self, path, clip_pre, tok, max_q=24, max_a=48):
self.rows = [json.loads(l) for l in open(path, encoding="utf-8")]
self.pre, self.tok, self.mq, self.ma = clip_pre, tok, max_q, max_a
def __len__(self): return len(self.rows)
def __getitem__(self, i):
r = self.rows[i]
img = self.pre(Image.open(r["image"]).convert("RGB"))
q = self.tok(r["question"], add_special_tokens=False).ids[:self.mq]
a = self.tok(r["answer"] + self.tok.eos_token, add_special_tokens=False).ids[:self.ma]
return img, torch.tensor(q), torch.tensor(a)
def collate(batch, pad):
pixel = torch.stack([b[0] for b in batch])
def padto(seqs):
m = max(len(s) for s in seqs)
return torch.stack([torch.cat([s, torch.full((m-len(s),), pad)]) for s in seqs])
return pixel, padto([b[1] for b in batch]), padto([b[2] for b in batch])
def main():
ap = argparse.ArgumentParser()
ap.add_argument("--stage", type=int, required=True, choices=[1, 2])
ap.add_argument("--data", required=True); ap.add_argument("--resume")
ap.add_argument("--epochs", type=int, default=1); ap.add_argument("--bs", type=int, default=8)
args = ap.parse_args()
dev = "cuda" if torch.cuda.is_available() else "cpu"
model = MiniLLaVA(dev)
if args.resume: model.proj.load_state_dict(torch.load(args.resume, map_location=dev))
if args.stage == 1: # 对齐:LLM 冻结,只训 projector
for p in model.llm.parameters(): p.requires_grad = False
lr = 1e-3
else: # 行为:projector+LLM 解冻
lr = 2e-5
params = [p for p in model.parameters() if p.requires_grad]
print(f"可训练参数:{sum(p.numel() for p in params)/1e6:.2f}M")
opt = torch.optim.AdamW(params, lr=lr, weight_decay=0.01)
ds = DS(args.data, None, model.tok)
dl = DataLoader(ds, batch_size=args.bs, shuffle=True,
collate_fn=lambda b: collate(b, model.tok.pad_token_id))
model.train()
for ep in range(args.epochs):
for i, (pixel, q, a) in enumerate(dl):
pixel, q, a = pixel.to(dev), q.to(dev), a.to(dev)
out = model(pixel, q, a)
opt.zero_grad(set_to_none=True)
out.loss.backward()
torch.nn.utils.clip_grad_norm_(params, 1.0)
opt.step()
if i % 20 == 0: print(f"ep{ep} step{i} loss={out.loss.item():.3f}")
tag = "stage1.pt" if args.stage == 1 else "final.pt"
torch.save(model.proj.state_dict(), tag)
print("saved →", tag, "(验收:3.2 §5 的三段对比图,训练前后各截 10 例)")
if __name__ == "__main__":
main()3.3 Connector 设计空间:Flamingo、BLIP-2 与开源双雄的答案
本章目标:横评 connector 的设计谱系——从 Perceiver Resampler 到 Q-Former 再到”MLP 赢了”,以及 Qwen-VL / InternVL 两个头部家族各自怎么解决 token 压缩与高分辨率。学完标准:能按”信息保真 / token 数 / 训练成本”三个轴给任何 connector 定位,并理解”Q-Former 之死”的教训。
1. 问题重述
3.1 的核心矛盾再具体一点:CLIP ViT-L 在 336px 下给 576 个 token——一条样本还扛得住;但高分辨率(文档、图表)要 2000+,多图对话和多帧视频直接爆炸。connector 的本质是信息瓶颈的设计权:压多少、按什么结构压、在哪一层压。
2. 谱系四站
2.1 Flamingo(2022):Perceiver Resampler + 门控交叉注意力
- Resampler:64 个可学习 query 对视觉特征做交叉注意力,输出固定 64 个 token——无论输入多少 patch,出口恒定;
- 更激进的:不在输入端拼接,而是在 LLM 每层之间插入交叉注意力层(文本 query 直接查视觉特征),用门控(初始为零的 tanh gate)保证训练起点等价于纯 LLM;
- 遗产:交叉注意力的”后融合”思想、门控稳定训练的技巧、图文交错数据格式(interleaved)。后续做视频/多图理解的工作普遍引用它。
2.2 BLIP-2(2023):Q-Former ——参数最重的 connector
- 32 个可学习 query + 一个完整的 BERT 式 Transformer 模块(~200M 参数),靠 ITC/ITM/ITG 三个损失预训练(从 BLIP 继承),再接 LLM;
- 出口仅 32 token,压缩率极高;
- 命运:被后续实验证明性价比不敌两层 MLP——LLaVA-1.5 用更简结构+更好数据全面超越 InstructBLIP。Q-Former 预训练的三个损失与 LLM 的使用方式错位,成为瓶颈。“Q-Former 之死”是本领域”数据 > 架构”的最强案例;但它的思想(learned query 池)在视频和 3D 里仍活着。
2.3 LLaVA 系:MLP 投影——简单者生存
- 两层 MLP,576 token 原样进 LM,压缩交给分辨率控制(336px)而不是模块;
- 阶段一用海量 caption 做对齐,比 Q-Former 的代理损失更直接服务下游。
2.4 现代 token 压缩工程(Qwen-VL / InternVL 的答案)
真正被产业保留下来的压缩发生在特征层面而非独立模块:
- Pixel Shuffle(InternVL / Qwen-VL 系):把空间上相邻的特征重排到通道维——例如 2×2 邻域重排,token 数 ÷4、通道 ×4,信息无损(只是重新打包),再用线性层压回原通道。这是当前开源 VLM 的主力压缩手法,InternVL 压 256 token,Qwen2-VL 动态压缩;
- 动态分辨率(Qwen2-VL 起,NaViT 思路):图像不 resize 到固定方块,按原生比例切 patch,token 数随内容变化——文档小字用高预算,缩略图用低预算。配套 M-RoPE(多模态旋转位置编码:时间/高/宽三维解耦的位置 ID);
- 大视觉塔路线(InternVL):与其压得更狠,不如把视觉塔做大做强(InternViT-6B 级别)再压——“视觉特征的质量决定压缩后的下限”。
3. 设计空间地图(给任何 connector 定位的三个轴)
| 轴 | 一端 | 另一端 | 权衡 |
|---|---|---|---|
| token 数 | 576(LLaVA-1.5) | 32(Q-Former) | 信息保真 vs LM 负担 |
| 模块参数 | 两层 MLP | 200M Q-Former | 训练简单 vs 表达能力 |
| 压缩位置 | 输入端投影 | LM 内部交叉注意力 | 管线简洁 vs 深度融合 |
结论公式(当前共识):MLP/轻投影 + pixel shuffle 压缩 + 动态分辨率 + 好数据。你做研究时若要动 connector,先证明”数据打不满”再动结构——否则审稿人一句”data scaling 就能解决”就拒了。
4. 自测题
- Resampler 和 Q-Former 的共同思想?(learned query 池把变长视觉特征池化成定长 token)
- Q-Former 输在哪里?(代理损失与 LLM 使用方式错位;同等算力下数据收益率更高——LLaVA-1.5 证明)
- pixel shuffle 为什么”无损”?压在哪?(空间信息重排进通道维,只是打包方式变化;后续线性层有损压缩)
- 动态分辨率解决固定方块的两个什么问题?(小图浪费预算 / 大图小字细节丢失)
- Flamingo 的零初始化门控和 LoRA 的 B 置零(2.6)共享什么哲学?(新模块从”恒等/不干扰”起点出发,不破坏预训练能力)
- M-RoPE 解耦了哪三个维度,为什么需要?(时间/高/宽;多帧多 patch 时单一位置序列表达不了时空结构)
5. 动手作业
- 读 LLaVA-1.5 论文的 ablation 表:列出”数据/分辨率/connector”三个因素的贡献量级——亲手验证”数据 > 架构”;
- 实现 pixel shuffle 压缩:
(B, 576, 1024)→(B, 144, 4096)(2×2 重排),用随机张量验证信息往返一致; - 用 transformers 加载 Qwen2.5-VL-3B(或 InternVL3-2B),数一张 448×448 图的视觉 token 数,对比同图 resize 到 336 的 CLIP 式 token 数——建立”现代 VLM 的 token 账单”直觉;
- 挑战:给 3.2 的迷你 LLaVA 把 576 token 换成 pixel shuffle 压缩到 144,对比阶段二的 loss 曲线和 caption 质量——你的第一个多模态结构消融。
案例 · 数值:576 个 token 如何无损变成 144 个
案例:pixel shuffle(2) 的完整流水账
CLIP 特征:24×24 网格,每位置 1024 维(合计 576 token)。
pixel shuffle(2):把相邻 2×2 的 4 个向量沿通道维打包 → 网格变 12×12 = 144 个位置,每位置 1024×4 = 4096 维。
信息核对: 个数字——一个都没丢,只是重新打包(这一步无损);随后接
Linear(4096→1024)才发生真正的有损压缩。读出设计的聪明处:把”压缩的学习”集中在最后那一个 Linear 层上(便宜、好训),而不是让 LLM 的注意力去硬扛 576 个 token(贵、平方复杂度)。这就是 3.3 正文说的”压缩发生在特征层面”的具体形状——InternVL 与 Qwen 系的公共底盘。
6. 延伸资源
- Flamingo / BLIP-2 论文——精读设计动机部分即可
- Qwen2-VL 技术报告(NaViT 式动态分辨率 + M-RoPE)——当代标准答案
- InternVL 系列报告——大视觉塔路线
3.4 视觉 Tokenizer:VQ-VAE 与 VQGAN——离散化是生成路线的地基
本章目标:理解”把图像变成离散 token”的全套技术——它是自回归生成图像(卷4.8 统一模型)和离散扩散的前提。学完标准:能手推 VQ-VAE 的 loss 和直通估计器,能解释 codebook 坍塌及现代解法,明白”tokenizer 质量封顶生成质量”这句话。
1. 为什么要把图像离散化
LLM 的成功配方是”离散 token 上的 next-token 预测”。想让同一个 Transformer 直接生成图像(统一模型的核心梦想,卷4.8),最顺的路是:先学一个”图像的 tokenizer”,把 256×256 图变成 256 个离散 token,图像就成了一种”外语”——和文本用同一词表、同一训练目标。这就是 Chameleon/Emu3 路线的前置条件。连续生成路线(扩散)不需要它,但离散路线离不开它。
2. VQ-VAE:编码 → 查表 → 解码
三段式(van den Oord et al., 2017):
- 编码器 :图像 → 连续特征图(如 256×256×3 → 32×32×d 的网格);
- 量化:网格上每个位置在码本(codebook,K 个可学习向量,如 8192 个)里找最近邻,用码本向量替换——图像从此变成 32×32=1024 个码本索引(离散 token!);
- 解码器 :量化后的特征 → 重建图像。
Loss 三件套:
- sg 是 stop-gradient:码本项只训码本,commitment 项只训编码器——两边互相靠近但各管各的( 常取 0.25);
- 直通估计器(straight-through estimator):最近邻查表不可导,前向用 、反向时把梯度原样抄给 ()。这是量化层可训练的唯一魔法——和 0.3 章手写的 backward 分摊是同一个思想的应用:梯度走不通就修一条近似的路。
3. Codebook 坍塌与两个工程解法
问题:K 个码本向量只有少数被用到(编码器只偏爱几个近邻),其余”饿死”——词表利用率低,等效词表缩水。解法:
- EMA 更新码本(VQ-VAE-2 标准):码本不参与梯度,直接向被分配到的编码器输出做指数滑动平均(0.4 章 EMA 的又一处出现);
- 死码重启:长期没被使用的码本向量重新随机初始化到当前 batch 的编码输出附近。
另外先验学习的分工要清楚:VQ-VAE 本身只学”重建”,token 的先验分布(哪种 token 序列像真图)交给下游模型学——原版用 PixelCNN,现代统一模型直接用大 Transformer(这正是”tokenizer + LM”解耦的架构意义:tokenizer 换得,LM 不用动)。
4. VQGAN:把”糊”治好——感知损失 + 对抗训练
VQ-VAE 重建偏糊(MSE 倾向平均脸)。VQGAN(2021)加两味药:
- 感知损失(perceptual/LPIPS):在 VGG 特征空间算距离——惩罚”像素对但看起来不对”;
- Patch 判别器:GAN 的判别器只看局部 patch,逼重建具备真实纹理。
结果:重建从”模糊蒙版”变”照片级”,离散 token 才有资格承载生成任务。此后谱系:ViT-VQGAN(Transformer 化 + 因子化码)、FSQ/LFQ(2023 后的现代简化:FSQ 干脆取消码本最近邻,用少量维度的低精度量化组合出码——没有坍塌问题、无需 EMA、训练稳,Magvit-v2 的 LFQ 让视频 token 化质量大涨——“删掉复杂机制反而更好”的又一案例)。
5. Tokenizer 是生成质量的天花板(本卷最重要的洞察)
下游 LM 生成的 token 序列,最终都要过 tokenizer 的解码器还原成图——它没见过的细节、重建不了的纹理,任何强大的 LM 都补不回来。“tokenizer 的重建上限 = 离散生成路线的上限”。这解释了 2023–2026 的持续投入:视频 token 化(MAGVIT-v2、Cosmos tokenizer)、高压缩比大码本、以及”为什么 Janus(卷4.8)干脆给理解和生成各配一套视觉编码”——理解要语义、生成要细节,一套 tokenizer 难两全。
6. 自测题
- VQ-VAE 三段式分别输出什么?(连续特征图 / 码本索引序列 / 重建图)
- 三项 loss 各自训练谁?sg 挡住了什么?(重建:全体;码本项:只码本;commitment:只编码器;防止 argmin 的梯度乱流)
- 直通估计器解决什么?(查表不可导——前向量化、反向抄送梯度)
- 码本坍塌是什么?两种解法?(少数码被垄断;EMA + 死码重启;FSQ 干脆取消码本)
- 为什么 MSE 重建偏糊、感知损失怎么治?(MSE 收敛到条件均值;VGG 特征空间惩罚”像素对但感知错”)
- “tokenizer 天花板”对统一模型研究意味着什么?(换更强 tokenizer 常比换更大 LM 收益更高;重建质量决定上限)
- VQ-VAE 和卷3.1 说的”原生融合”如何接上?(VQ token 与文本同表同目标——Transformer 一套 autoregressive 吃两模态)
7. 动手作业
- 在 MNIST 上实现迷你 VQ-VAE(编码器 2 层 CNN、码本 64、commitment 0.25),记录码本利用率(被用到的码占比)——亲眼看坍塌;
- 给它加 EMA 更新与死码重启,对比利用率曲线;
- 加载一个工业级图像/视频 tokenizer 的开源实现(如 MAGVIT-v2 或 Cosmos tokenizer),对比你的迷你版:码本规模、利用率、重建质量差距各有多大;
- 算账:8192 码本 × 32×32 网格的”图像序列”的信息上限 vs 一张 PNG 同尺寸的体积——体会”离散 token 是有损压缩”。
8. 延伸资源
- VQ-VAE 论文(Neural Discrete Representation Learning)——sg 与 commitment 的出处
- VQGAN 论文(Taming Transformers)——taming 之名即”驯服 Transformer 生成图像”
- “Language Model Beats Diffusion — Tokenizer is Key”(2024)——tokenizer 决定论的证据文
3.5 开源双雄精读:Qwen-VL 与 InternVL 系列技术报告
本章目标:把 3.1–3.3 的框架用在两个真实家族上——按 6.1 的”配置清单”读法拆解 Qwen-VL 与 InternVL 的演化线,并学会”选底座”的决策方法。学完标准:能给任何开源 VLM 填出配置卡,并能为你 8.9 的选题选出合适的底座。
1. 为什么要精读技术报告
会议论文只给你方法创新,技术报告给你的是完整配置单:数据配比、训练阶段表、消融取舍、失败尝试。对做研究的人来说,报告比论文更接近”可复制的真相”——它就是 6.1 说的”30 分钟抽卡归档”的最佳对象。
2. Qwen-VL 演化线(阿里,Apache 开源)
| 版本 | 关键变化 | 对应本笔记知识点 |
|---|---|---|
| Qwen-VL(2023) | resampler 压缩视觉 token(BLIP-2 血统) | 3.3 的 learned query 路线 |
| Qwen2-VL(2024) | NaViT 式动态分辨率(原生比例切 patch)+ M-RoPE(时/高/宽三维位置) | 3.3 §2.4,token 压缩的现代答案 |
| Qwen2.5-VL(2025) | grounding(绝对坐标指框)与 GUI agent 能力强化、小时级视频理解、文档解析 | 视觉 agent(5.6)的底座 |
| Qwen3-VL(2025–26) | early-fusion:视觉 token 从预训练第一天进场(不再”先语言后视觉”);2B→235B 全尺寸;interleaved 多图上下文 | 3.1 路线三(原生融合)成为现实 |
读报告时盯三条线:① 视觉 token 怎么产生和压缩;② 训练分几阶段、各阶段数据配比;③ RL/后训练做了什么(Qwen 系在 grounding/agent 上的后训练强度逐代加大)。
3. InternVL 演化线(上海AI Lab,MIT 开源)
| 版本 | 关键变化 | 对应知识点 |
|---|---|---|
| InternVL(2023) | 自研大视觉塔 InternViT-6B——“与其压狠不如视觉强” | 3.3 的大视觉塔路线 |
| InternVL1.5/2(2024) | pixel shuffle 压缩(token ÷4);尺寸矩阵化(1B–26B 全谱系) | 3.3 主力压缩手法 |
| InternVL3(2025) | 原生多模态预训练(和 Qwen3-VL 同趋势);SFT+RL 一体化 | 3.1 路线三 |
| InternVL3.5(2025–26) | Cascade RL(离线+在线两级);ViR 视觉分辨率路由(按图复杂度动态分配 token 预算——“不重要的图少花 token”);推理效率对齐商用模型 | 效率化(5.8)的教科书案例 |
血统差异一句话:Qwen 起于 LLM(语言强、agent 生态大),InternVL 起于视觉塔(视觉细节强、文档/OCR 传统深)。两家共同汇入同一终点:动态分辨率 + 原生融合 + RL 后训练 + agent 能力——这四条就是 2026 年开源 VLM 的”公约数配置”。
4. 对比卡(精读后自己填全的模板示例)
| 维度 | Qwen3-VL | InternVL3.5 |
|---|---|---|
| 视觉塔 | 自研 ViT(early-fusion 联训) | InternViT(大塔路线) |
| token 策略 | 动态 patch + 压缩 | pixel shuffle + ViR 路由 |
| 位置编码 | M-RoPE 系 | RoPE(细节见报告) |
| 预训练范式 | early-fusion | 原生多模态预训练 |
| 后训练 | SFT + RL(agent/grounding 重) | SFT + Cascade RL |
| 强项场景 | GUI agent、视频、指框 | 文档/OCR、细粒度视觉 |
| 尺寸谱系 | 2B→235B | 1B→大尺寸,小尺寸效率突出 |
5. 科研选底座的决策法
- 尺寸对齐算力(2.10 阶梯):2B/4B 是 4090 甜点;
- 任务对血统:做文档/OCR/细粒度 → InternVL 系概率占优;做 agent/grounding/视频 → Qwen 系(生态与工具链成熟);
- 许可证与生态:两家都开放商用,但 Qwen 的微调工具链(LLaMA-Factory/MS-SWIFT 支持最全)对学生最友好;
- 留一手:底座是可替换变量——你的数据集与评测协议(A1)才是资产。实验设计时把”底座”作为对照实验的一个维度(两个底座各跑一遍,结论可信度立刻上档)。
6. 自测题
- Qwen2-VL 解决”固定方块分辨率”的两件武器?(NaViT 动态 patch;M-RoPE 三维位置)
- InternVL 的”大视觉塔”哲学与 pixel shuffle 的关系?(先保证视觉特征质量,再无损重排压缩——3.3 的轴)
- InternVL3.5 的 ViR 在优化什么?(视觉分辨率路由——按图复杂度分配 token 预算,效率视角)
- 两家共同汇入的”公约数配置”四条?(动态分辨率/原生融合/RL 后训练/agent 能力)
- 选底座时为什么”你的数据集与协议才是资产”?(底座可替换可对照;数据与评测沉淀为长期研究资产)
- early-fusion 相比 connector 训练贵在哪、好在哪?(全价预训练 vs 模态深度融合——3.1 的结论在双雄身上的印证)
7. 动手作业
- 选一份报告(建议 Qwen2.5-VL 或 InternVL3),用 6.1 配置清单模板填出完整配置卡(架构/数据/阶段/RL/评测五张卡);
- 用 vLLM 跑通两个家族各一个小尺寸模型(2B 级),对同一批图(用你 A1 的样例)出对比表——你的第一次”双底座对照”;
- 把两家的”阶段训练表”并排抄录,标注哪些阶段冻结视觉塔、哪些解冻——对照 3.2 的 LLaVA 两阶段,写 200 字演化心得;
- 挑战:在报告里找出一个”未消融的设计选择”(例如 ViR 的路由阈值)——把它记入你的选题孵化器(6.2 §5)。
8. 延伸资源
- Qwen2.5-VL / Qwen3-VL 技术报告(arXiv)
- InternVL3 / 3.5 技术报告
- MS-SWIFT / LLaMA-Factory 的模型支持列表——工程侧的底座兼容性速查
3.6 文档理解与 OCR-free:让 VLM 读懂 PDF
本章目标:讲清”文档智能”从 OCR 流水线到端到端 VLM 的范式更替——它是多模态落地量最大的应用(办公/金融/政务/数据引擎),也是你 8.8 题跋 OCR 的技术基础。学完标准:能画出两条路线的对比图,知道现代 PDF 解析管线的工程形态。
1. 两条路线
传统 OCR 流水线:文本检测(找到字在哪)→ 文本识别(认出是什么字)→ 版面分析(标题/段落/表格的层级)→ 语义理解(NLP)。四段独立、各段误差累积、每段都要单独维护。
OCR-free 端到端:文档图(整页)直接进 VLM → 直接输出结构化结果(答案/markdown/JSON)。胜利原因:① 版面与语义联合建模(“这是标题”和”标题说了什么”互相支持);② 一套模型吃所有文档类型;③ 输出直接是下游可用的结构。
但 OCR 没死:高精度场景(车牌/票据金额)、边缘设备、以及数据引擎的前端(海量 PDF 转文本)仍是专用 OCR 的地盘——正确认知是”端到端 VLM 为主,专用 OCR 为辅”的混合架构。
2. 演化线(记住五个名字的因果)
- Donut(2021):OCR-free 开山——Swin 编码器 + BART 解码器,直接从文档图生成结构化文本;
- Pix2Struct(2022):截图预训练(遮罩恢复 HTML 结构)——“网页/文档也是可以自监督的”;
- mPLUG-DocOwl / UReader(2023–24):LLaVA 范式进文档(高分辨率切片进 VLM)——文档理解并入 VLM 主流;
- GOT-OCR2.0(2024):“general OCR theory”——统一端到端把文档/公式/表格/乐谱全转成文本/markdown;
- 工业管线(2024–25):MinerU、olmOCR、Qwen-VL 文档解析——专为 LLM 数据引擎设计的 PDF→markdown 大规模管道(清洗、版面还原、表格结构化)。
你每天都在受益于第 5 条:各家 LLM 的知识里,PDF 转出来的语料占比极高——文档解析是数据引擎(5.2)的隐形基础设施。
3. 文档 VLM 的三个技术要点
- 分辨率优先:小字(合同条款/印章边注)是文档的命——高分辨率/切片策略(AnyRes,1.4/3.3)在文档场景从”加分项”变成”生死线”;token 账在这最疼(一页 4K 扫描件数万 token);
- 结构化输出:目标不是”描述这页纸”而是还原版面语义——markdown 标题层级、表格转 HTML、公式转 LaTeX;训练数据的输出格式设计比模型更重要(5.2 的领域应用);
- 表格与图表:表格要还原行列结构(不是 OCR 一串数字)、图表要读出数据系列(ChartQA 能力)——两者是文档智能与 5.1 可验证奖励的交汇(读数可自动判分)。
4. 评测与你的接口
基准:DocVQA(文档问答)、ChartQA(图表问答)、OCRBench(综合)、以及各家自建的解析评测(markdown 还原相似度)。与你的三处接口:① 8.8 的题跋/印章处理——书法 OCR 是文档智能的艺术分支(异体字/草书=更高难度,空白即选题);② 5.6 的屏幕理解——GUI 本质是”活的文档”;③ 数据引擎就业面——MinerU 类管线的开发与优化是真实岗位。
5. 自测题
- OCR-free 胜出的两个原因?(版面语义联合建模/一套模型全类型)
- “OCR 没死”的三个据点?(高精度票据/边缘端/数据引擎前端)
- 文档场景为什么分辨率是生死线?(小字是文档核心信息——token 账最疼处)
- 表格解析和表格 OCR 的区别?(还原行列结构语义 vs 认出一串字)
- MinerU 类管线在 LLM 产业里的角色?(PDF→训练语料——数据引擎的隐形基础设施)
- 题跋 OCR 的难点与机会?(异体字草书+图文关联——艺术分支的空白题)
6. 动手作业
- 用 MinerU(或 olmOCR)解析一份中文学术 PDF,检查表格/公式的还原质量,写 200 字体检报告;
- 用 Qwen-VL(或 GOT)对同一页做端到端解析,对比两条路线的输出;
- 对 8.1 素材里的一幅中国画题跋做 OCR 尝试,记录失败模式——D2 选题的第一手证据;
- 挑战:读 Donut 论文 §1,用三句话讲清”为什么 2021 年的人们相信可以跳过 OCR”。
7. 延伸资源
- Donut / GOT-OCR2.0 论文——两条路线的代表作
- MinerU / olmOCR repo——工业管线现状
- DocVQA / OCRBench——评测体系
3.7 多模态评测体系与陷阱
本章目标:看懂 VLM 的成绩单从哪来、哪些分数不能信,以及怎么为你自己的项目搭一套干净评测。这一章直接服务于 A1(看画基准)和所有 8.9 选题的验收环节。学完标准:能读懂任何 VLM 榜单的评测协议,能说出五种主要陷阱及对策。
1. 基准地图(按能力分家)
| 能力域 | 代表基准 | 考什么 |
|---|---|---|
| 综合知识推理 | MMMU、MMBench、MME | 大学级图文题、通用理解 |
| 视觉数学/图表 | MathVista、ChartQA | 图上读数、几何推理 |
| 文档/OCR | DocVQA、TextVQA | 文字识别与版面理解 |
| 幻觉专项 | POPE、HallusionBench、AMBER | 是否编造图中不存在的对象/关系 |
| 指框 grounding | RefCOCO 系 | 按描述给坐标——可精确判分(5.1 喜欢的奖励源) |
| 视频 | Video-MME | 长视频时序理解 |
| Agent/GUI | ScreenSpot、OSWorld | 截图定位、真实任务完成 |
| 开放问答/生成 | MM-Vet、WildVision | 无固定答案,靠裁判模型 |
2. 评测协议的两大家法
- 封闭式判分:选择题(对/错)或短答案精确匹配——客观、便宜、可复现;风险:模型靠选项偏置答题(都选 A)、格式猜答案;
- LLM-as-judge:开放回答交给 GPT 级裁判模型按 rubric 打分——贴近真实使用;风险:裁判偏爱长回答/自家风格、位置偏见、可复现性差(换裁判模型分数漂移)。
工程正确姿势:两类并用——封闭式出主表数字,judge 法出开放能力的定性证据,且 judge 校准(抽 10% 人工对齐,报告一致率)。
3. 五大陷阱与对策(本章核心)
- 数据污染(contamination):基准题混进训练数据——榜单分数是”背题”不是能力。检测:n-gram 重叠扫描、字符串探针、扰动测试(改数字/换图重测,掉分暴跌=背题实锤)。对策:报告污染扫描结果;自己造数据时严格隔离留出集;
- 选择题应试技巧:选项长度/位置偏置——模型不看图也能蒙 40%+。对策:必须跑”盲测基线”(去掉视觉输入的准确率),真实能力 = 有图减无图的增量(5.1 的红灯检查通用化);
- 裁判偏见:LLM-as-judge 的风格/长度/身份偏好。对策:rubric 具体化(逐条打分非总分)、双裁判交叉、位置互换重判;
- 协议敏感性:分辨率、prompt 模板、few-shot 数量一变分数就动——很多”超越 SOTA”只是协议红利。对策:评测协议在实验开始前冻结并写死(版本、分辨率、模板、seed 全记录);
- 饱和与区分度:头部模型把老基准刷到 90%+,测不出差异。对策:用最新/更难的基准(MathVista 类),或自建领域留出集——这恰恰是 8.9/A1 的战略意义:别人的榜单迟早饱和,自己的干净基准是长期资产。
4. 给自己项目搭评测的清单(A1 蓝图)
- 分层:按 8.1 三层(形式/内容/语境)或你的研究维度设计题集,每层 ≥100 题;
- 协议冻结:题型(选择/短答/judge)、prompt 模板、判分规则、分辨率——先写文档后跑实验;
- 三件套基线:随机基线(选择题主)+ 盲测基线(无图)+ 一个强模型参照(划能力上限);
- 人工校准子集:50–100 题人工标注,校验自动判分一致率;
- 发布 datasheet:数据来源、标注协议、已知局限——学术规范,也是导师眼中加分的科研素养。
5. 自测题
- 封闭式与 judge 法各自的死穴?(应试技巧与选项偏置;裁判偏见与可复现性差)
- 扰动测试怎么暴露背题?(改数字换图后分数暴跌——模型记住的是答案不是方法)
- 为什么”有图减无图的增量”比绝对准确率诚实?(增量才是视觉能力的度量,绝对值含语言先验)
- 协议冻结防什么?(事后调协议凑分数——自己骗自己的最常见形式)
- 自建基准的战略价值与成本?(长期资产+领域话语权 vs 标注与校准成本——所以选 A1 当第一题)
- datasheet 是什么、写给谁看?(数据集的来源/协议/局限说明书;给使用者和审稿人)
6. 动手作业
- 跑 lmms-eval(开源评测框架)给一个 2B VLM 出 MMMU 子集 + POPE 成绩单,阅读它的评测配置文件——工业协议长什么样;
- 做一次盲测实验:同模型同题集,遮图 vs 正常,算”视觉增量”——亲手体会陷阱 2;
- 给你的 A1 写”协议冻结文档”(§4 第 2 条)+ 30 条样例题;
- 挑战:对某个”刷榜结果”复刻其协议再做扰动测试,写 300 字判断(这是 C 类分析文的种子)。
7. 延伸资源
- lmms-eval(LMMs-Eval 框架)——开源评测的标准工具链
- MMMU / POPE / HallusionBench 原论文——三类基准的设计动机
- 《Data contamination survey》类综述——污染检测方法集
3.8 数据为中心的 VLM:具体案例研读
本章定位:5.2 讲了方法论(指标、配方、风险),这一章读具体的菜谱——LLaVA 系数据谱系的构成、头部模型报告里的数据配比表读法,以及开源数据集的实操盘点。学完标准:能读懂任何 VLM 报告的数据章节,并能为你 8.5/8.6 的领域数据选取参照模板。
1. LLaVA 系数据谱系(开源数据的骨架样本)
| 数据集 | 规模/构成 | 服役阶段 | 关键设计 |
|---|---|---|---|
| LCS558K | 55.8 万条详情 caption | 阶段一对齐 | 强模型重写 caption(“详细描述”) |
| LLaVA-Instruct 665K | 对话 158K + 详细描述 23K + 复杂推理 86K + VQA(VQA/OCR/科学) | 阶段二 SFT | 用 GPT-4 从 caption+检测框合成——“学术任务数据”的配方本体 |
| LLaVA-OneVision 系 | 单图/多图/视频混合,配比公开 | 三域统一 | 数据配比是它的核心贡献之一 |
读法要点:665K 的内部构成(四类任务的比例)比总量更重要——它定义了”通用 VLM SFT”的默认配方,后来者都在此基础上增删。作业里要你真的去数一遍(HF 上有现成分区)。
2. 报告里的数据章节怎么读(以双雄为例的读表法)
3.5 的配置清单里,数据部分通常给一张”预训练/SFT 各阶段的数据源与 token 数”表。读表三问:
- 各类数据的比例:图文对 vs 纯文本 vs 多图/视频的 token 占比——比例即设计哲学(Qwen 系重 agent/OCR 语料的占比逐年上升,这就是它的能力重心变迁史);
- 阶段划分与冻结策略的对应:哪类数据配哪个阶段(caption 配对齐阶段、指令配 SFT、agent 轨迹配后训练——3.2 两阶段框架的扩展);
- 合成与再标注的声明:哪些数据是模型生成/重标注的(ShareGPT4V 式”强模型重注”已成行业标配——5.2 §2 的工艺在头部模型的落地)。
3. 开源数据集实操盘点(选数据先看这张单)
| 数据集 | 类型 | 用途 |
|---|---|---|
| LLaVA-Instruct 665K | 通用指令 | SFT 起步标配(3.2 复现用) |
| ShareGPT4V | 详情 caption | 阶段一升级(“只换 caption 全基准涨”的出处) |
| Cambrian-1 数据包 | 策展多源 | 数据配比研究(5.2 的纲领配套) |
| ALLaVA / Cauldron | 混合指令 | 通用 SFT 的替代选项 |
| ChartQA/DocVQA/GeoQA | 可验证垂直数据 | RLVR/领域评测(5.1 配方) |
| WikiArt/ArtBench + 你的蒸馏 | 艺术领域 | 你的 8.5/8.6 领地 |
选取原则(5.2 §4 的落地):固定模型与协议,一次只换一个数据变量;每引入一个新数据集先跑”数据体检”(7.5 §2 的质检 + 3.7 的污染扫描)。
4. 领域数据的”配方迁移”练习(你的方向)
把 LLaVA 配方迁移到艺术领域的具体设计(8.5 W3–6 的数据节细化):
- 对齐阶段数据:WikiArt 图 + 强模型详情 caption(画家/流派/构图/色彩的形式层描述——8.1 词汇表当 prompt 素材);
- SFT 数据四类对应:对话(看画多轮问答)/ 详细描述(单画深度分析)/ 复杂推理(“从笔触推流派”的 CoT)/ VQA(流派分类题——可验证);
- 配比假设:通用数据与领域数据 1:1 起步(防遗忘,2.5 §5),领域内四类按 2:2:1:1——这个配比就是你的第一个消融对象。
5. 自测题
- 665K 的四类构成是什么?为什么比总量重要?(对话/详注/复杂推理/VQA——构成定义任务分布即能力形状)
- “学术任务数据”的合成原料是什么?(caption + 检测框 + GPT-4——从旧标注生成新指令)
- 读报告数据表的三问?(比例/阶段对应/合成声明)
- ShareGPT4V 的核心发现一句话?(只换详情 caption,全基准普涨——数据质量红利)
- 领域迁移时为什么要 1:1 混通用数据?(防灾难性遗忘——2.5 的结论在配比上的落地)
- 新数据集入库前的两道检查?(7.5 质检 + 3.7 污染扫描)
6. 动手作业
- 下载 LLaVA-Instruct 665K,统计四类构成并画饼图——验证本章 §1 的表;
- 抽 50 条人评质量(格式/正确性/多样性),写 200 字”数据体检报告”;
- 按 §4 给你的艺术领域写出”数据配方 v0”(四类各多少条、来源、合成 prompt 模板)——8.5 实验的直接输入;
- 挑战:读 LLaVA-OneVision 报告的数据章节,做一页”配比对照表”(它 vs 665K 的哲学差异)。
7. 延伸资源
- LLaVA-1.5 / LLaVA-OneVision 报告数据章节——配方本体
- ShareGPT4V / Cambrian-1 论文(5.2 已列,此处读数据构成细节)
- HuggingFace 上的 LLaVA-Instruct 数据卡——字段说明与分区
4.1 生成模型地图:五大家族一张图
本章目标:在钻进扩散模型的数学之前,先拿到全图——生成式建模有哪些家族、各自赌的是什么、谁在什么场景活着。学完标准:能一句话说清五大家族各自的”建模范式”,并解释为什么 2020 年后天平倒向扩散/流。
1. 生成式在解什么问题
1.1 章说过:判别式学 ,生成式学 或 (c 是文本等条件)。“学 “落地成两个可考核的能力:采样(生成新样本)和密度评估(给样本打概率,研究用)。所有家族的差异,本质是怎么表示和逼近这个分布。
2. 五大家族速览
| 家族 | 建模范式 | 强项 | 死穴 | 现状 |
|---|---|---|---|---|
| 自回归 AR | 链式法则分解 | 训练稳定、与 LLM 同构、可无限续写 | 串行采样慢;图像要离散化(3.4) | 统一模型路线的引擎(GPT/Janus/Chameleon) |
| VAE | 潜变量 + 变分下界(ELBO) | 快、表征可插值 | 重建糊(优化下界而非似然) | 独立生成已边缘化;活着:SD 的压缩器(4.4) |
| GAN | 隐式分布 + 生成器/判别器对抗 | 快(一步采样)、锐利 | 训练不稳、模式坍塌、难评测 | 生成主体已让位;活在超分/解码器里 |
| Diffusion | 迭代去噪:学每一步的”去噪方向” | 训练稳、多样性好、可控性强 | 多步采样慢(被蒸馏缓解) | 图像/视频生成的统治者 |
| Flow | 学一条把噪声搬运到数据的速度场,ODE 采样 | 训练最简、路径直、少步采样 | 理论较新,生态在迁移中 | 当前最先进(SD3/FLUX) |
3. 两条轴看懂全部恩怨
- 显式密度 vs 隐式分布:AR/VAE/Diffusion/Flow 都(以不同方式)和概率挂钩——可算 loss、可做 likelihood;GAN 只有判别器这个”裁判”,没有显式概率——所以 GAN 训练如走钢丝(生成器与判别器的平衡)且难评测(没有标准 loss 曲线可看);
- 一步 vs 迭代:GAN/VAE 一步出图(快);AR/Diffusion/Flow 逐步走(慢但稳)。2020–2025 的主线就是”迭代派的稳定性”打败”一步派的锐利”——GAN 时代生成人脸清晰但多样性差、模式坍塌(十张图九张同款);扩散多样性/保真双高,计算便宜后锐利劣势消失。而现在蒸馏与流模型正在把”迭代”重新变快——历史在螺旋回升。
4. 为什么你要主学扩散/流
- 产业在用:SD/FLUX/可灵/即梦全是这条线;理解类 VLM 之外的一切”生成”岗位都考它;
- 科研活跃:可控生成、一致性模型、流匹配理论、统一模型——论文产出密度最高的生成子领域;
- 数学回报最高:扩散的”去噪即梯度场”思想、流的”直线搬运”思想,学透之后你对”模型在学什么”的直觉会上一个台阶;
- 与卷3 的接口现成:VAE 活在 SD 的压缩器里(4.4)、VQ 活在统一模型里(3.4/4.8)——五大家族不是五选一,而是当前系统里的不同器官。
5. 自测题
- GAN 的”隐式分布”是什么意思?带来哪两个工程问题?(没有显式概率密度;训练不稳 + 难评测)
- 模式坍塌是什么?哪家的死穴?(生成器把多个模态塌到一个安全答案;GAN)
- VAE 在 2026 年以什么身份活着?(SD/FLUX 的潜空间压缩器——4.4)
- AR 生成图像的前置条件是什么?(离散 tokenizer,3.4)
- “迭代派的稳定性打败一步派的锐利,蒸馏又把迭代变快”——概括了哪十年的什么主线?(2020s 生成模型主导权变迁:GAN→扩散→快采样化)
- Flow 和 Diffusion 最朴素的一句话区别?(学”逐步去噪的概率修正” vs 学”噪声到数据的直线速度场”——4.5 展开)
6. 动手作业
- 画五大家族地图(横轴:一步↔迭代;纵轴:显式↔隐式),把代表模型标上去;
- 各下载一张 2018 年 StyleGAN 人脸和一张 2025 年扩散人脸对比,用 8.1 的”明暗五调子/纹理”语言写 200 字差异分析——感受”锐利 vs 多样性”的历史具体含义。
7. 延伸资源
- Lilian Weng 博客《What are Diffusion Models?》——本章到 4.3 的最佳伴读
- 《难以置信的生成模型之旅》类综述视频(B 站搜”生成模型 五大家族”)——快速过图
4.2 DDPM 原理与从零实现
本章目标:把扩散模型的”加噪—去噪”从玄学变成你能手推、能手写的算法。学完标准:能从零推导闭式加噪公式,能解释”预测噪声”这个训练目标从哪来,并在 MNIST 上跑通一个 50 行的迷你扩散模型。
1. 前向过程:主动把图搅成噪声(不需要学习)
定义一个马尔可夫链,每步加一点高斯噪声,T 步后图像变成纯噪声:
是噪声强度表(schedule,从 1e-4 涨到 0.02 之类)。关键推导(必会):令 、,反复代入高斯叠加性,得到任意时刻 t 的闭式解——不用逐步迭代,一步采样:
读法: 是”原图按 衰减 + 噪声按 注入”的混合。t 小偏原图,t 大近纯噪声——训练时对每个样本随机抽一个 t,立刻得到带标签的”输入-答案”对(输入 ,答案 ε),这就是自监督信号。
2. 反向过程:学”去噪方向”(模型登场)
真实反向 不可得(需要整张图的数据分布),所以训练神经网络 去逼近它。贝叶斯代入后可把 重参数化——模型实际要预测的是混在 里的噪声 ε:
这个 MSE 就是 DDPM 的全部训练目标(DDPM 论文证明它是 ELBO 的简化等价——严格推导选修,直觉必修)。
直觉版理解(推荐记忆这个):预测噪声 = 预测”去噪方向”。把 改写一下,它近似于在学 ——数据对数密度的梯度(score)。也就是说,模型学的是”在当前位置,往哪个方向走概率密度更高”。去噪生成的本质是沿着学到的密度梯度,从噪声一路走到数据流形。这句话打通了扩散和”压缩即智能”(2.1)——都在学数据的结构。
3. 训练与采样算法(各 4 行,背下来)
训练:① 取 ;② 随机 t、随机 ε;③ 闭式合成 ;④ 梯度下降 。
采样:从 开始,循环 :
(减去预测噪声的贡献,再加一点随机性 ;t=1 时停止加噪。)1000 步走完,噪声里”长”出一张图。
4. 从零实现(MNIST,50 行核心)
import torch, torch.nn as nn, torch.nn.functional as F
betas = torch.linspace(1e-4, 0.02, 500) # T=500(MNIST 够了)
alphas, abar = 1-betas, torch.cumprod(1-betas, dim=0) # α 与 ᾱ 的闭式表
def add_noise(x0, t): # 闭式加噪
a = abar[t].view(-1,1,1,1)
eps = torch.randn_like(x0)
return a.sqrt()*x0 + (1-a).sqrt()*eps, eps
class Denoiser(nn.Module): # 简化网络:真实用 U-Net
def __init__(self):
super().__init__()
self.t_emb = nn.Sequential(nn.Embedding(500, 64), nn.Linear(64, 64), nn.SiLU(), nn.Linear(64, 64))
self.net = nn.Sequential( # 仅示意,U-Net 见 4.4
nn.Conv2d(1, 64, 3, 1, 1), nn.SiLU(),
nn.Conv2d(64, 64, 3, 1, 1), nn.SiLU(), nn.Conv2d(64, 1, 3, 1, 1))
def forward(self, xt, t):
h = self.net(xt) # 真实实现要把 t_emb 调制进每层
return h
model = Denoiser()
for step in range(20000): # 训练
x0 = next(loader) # MNIST batch, 归一化到 [-1,1]
t = torch.randint(0, 500, (x0.size(0),))
xt, eps = add_noise(x0, t)
loss = F.mse_loss(model(xt, t), eps) # 全部训练目标就这一行
...
@torch.no_grad()
def sample(n=8):
x = torch.randn(n, 1, 28, 28)
for t in reversed(range(500)):
eps = model(x, torch.full((n,), t))
a, ab = alphas[t], abar[t]
x = (x - (1-a)/ (1-ab).sqrt() * eps) / a.sqrt() # 去噪一步
if t > 0: x = x + betas[t].sqrt() * torch.randn_like(x)
return x
(网络按理应把 t 编码注入每层——教学版从简,作业里补全;U-Net 结构与注入方式见 4.4。)跑通后你会看到:采样从一团雪花里逐渐浮现数字——这是你亲手实现的”从噪声中创造”。
5. 预测目标的三胞胎(为 4.5 埋线)
同一个网络可以学三种”答案”:ε-pred(预测噪声,DDPM)、x0-pred(直接预测原图)、v-pred(预测二者的组合 )。数学上可互相换算,但训练动态和数值稳定性不同——v-pred 在低噪声端更稳,是渐进式蒸馏和流模型(4.5 的速度场正是它的推广)的桥。知道存在即可,别背公式。
6. 自测题
- 闭式加噪公式的两个分量各是什么?它让训练获得了什么?( 衰减信号 + 注入噪声;任意 t 一步采样 → 海量自监督对)
- 为什么反向过程必须”学”而前向不用?(前向是人为定义的马尔可夫加噪;反向依赖未知数据分布)
- 训练 loss 的直觉含义是什么?(学数据对数密度的梯度方向——score matching)
- 采样循环里 σ_t z 的作用?去掉会怎样?(随机性,保分布多样性;去掉=确定性轨迹,多样性降——正是 DDIM 的思路)
- T=1000 而采样也 1000 步,慢在哪?预感怎么破?(串行迭代;见 4.3 跳步采样)
- ε/x0/v 三种预测目标的关系?(可互相换算的三种参数化;稳定性与下游蒸馏的适配不同)
7. 动手作业
- 跑通 MNIST 迷你版(补全 t 注入:把
t_emb过 MLP 后 reshape 加到特征图上),存 8 张采样过程的中间帧 gif; - 手推闭式公式:从 出发两步归纳到 (高斯叠加:均值方差各自相加);
- 把 β schedule 换成 cosine(Nichol & Dhariwal)对比采样质量——体会 schedule 不是小事;
- 挑战:给迷你模型加条件(0–9 数字标签,用 4.3 的 CFG 思路),实现”指定数字生成”。
图解与案例 · 加噪-去噪的一来一回
flowchart LR
subgraph F["前向(不需要学习)"]
X0["x₀ 原图"] -->|"√ᾱ_t·x₀ + √(1−ᾱ_t)·ε"| XT["x_t 加噪图"]
end
XT --> NET["网络 ε_θ(x_t, t)<br>任务:指认出噪声 ε"]
subgraph R["反向(迭代采样)"]
NET --> X1["x_{t−1} = 减去预测的噪声贡献"]
end
X1 -. "重复 t−1 步直到 x₀" .-> NET案例:给一个像素加噪(数字全算出)
取单像素 ,某时刻 (信号只剩 1/4),采样噪声 :
训练时:把 和 喂给网络,要求它指认出当初那个 0.8,loss = 。
读出三点:① 信号被 √ᾱ 衰减、噪声被 √(1−ᾱ) 放大——t 就是信噪比的旋钮;② 模型的任务永远不变:从混合物里指认噪声;③ 因为闭式公式,任意 t 的训练样本可以一步合成——这是扩散训练可以大规模并行的根基。
8. 延伸资源
- DDPM 论文(Ho et al., 2020)+ Lilian Weng 博客——精读组合拳
- 李沐《论文精读》DDPM 一期——推导全程带画
- Hugging Face《Annotated Diffusion》——带注释的完整实现
附录 · 完整可运行脚本:ddpm_mnist.py(含小 U-Net)
依赖:
torch torchvision。4.2 §4 教学版的完整化:真 U-Net(含时间注入与跳跃连接)、余弦可换 schedule、采样出网格图。
# ddpm_mnist.py —— MNIST 上的完整 DDPM(T=400)
import torch, torch.nn as nn, torch.nn.functional as F, math
from torchvision import datasets, transforms, utils
from torch.utils.data import DataLoader
T = 400
betas = torch.linspace(1e-4, 0.02, T)
alphas, abar = 1 - betas, torch.cumprod(1 - betas, 0)
def time_emb(t, dim=64): # 正弦时间嵌入(1.3 位置编码同款)
half = dim // 2
freqs = torch.exp(-math.log(10000) * torch.arange(half) / half)
ang = t[:, None].float() * freqs[None]
return torch.cat([torch.sin(ang), torch.cos(ang)], 1)
class Block(nn.Module):
def __init__(self, cin, cout):
super().__init__()
self.c1, self.c2 = nn.Conv2d(cin, cout, 3, 1, 1), nn.Conv2d(cout, cout, 3, 1, 1)
self.n1, self.n2 = nn.GroupNorm(8, cout), nn.GroupNorm(8, cout)
self.tmlp = nn.Linear(64, cout) # 时间注入:加到特征上
self.skip = nn.Conv2d(cin, cout, 1) if cin != cout else nn.Identity()
def forward(self, x, t):
h = F.silu(self.n1(self.c1(x)))
h = h + self.tmlp(t)[:, :, None, None]
h = F.silu(self.n2(self.c2(h)))
return h + self.skip(x)
class UNet(nn.Module):
def __init__(self, ch=64):
super().__init__()
self.inp = nn.Conv2d(1, ch, 3, 1, 1)
self.d1, self.d2 = Block(ch, ch), Block(ch, ch * 2)
self.pool = nn.Conv2d(ch, ch, 4, 2, 1) # 步长卷积下采样
self.mid = Block(ch * 2, ch * 2)
self.u2 = Block(ch * 4, ch), self.u1 = Block(ch * 2, ch)
self.out = nn.Conv2d(ch, 1, 3, 1, 1)
def forward(self, x, t):
te = time_emb(t)
x0 = self.inp(x) # 28
x1 = self.d1(x0, te) # 28 (skip1)
x2 = self.pool(x1); x2 = self.d2(x2, te) # 14 (skip2)
m = self.mid(F.max_pool2d(x2, 2), te) # 7
u = F.interpolate(m, scale_factor=2) # 14
u = self.u2[0](torch.cat([u, x2], 1), te)
u = F.interpolate(u, scale_factor=2) # 28
u = self.u1[0](torch.cat([u, x1], 1), te)
return self.out(u)
def add_noise(x0, t):
a = abar[t].view(-1, 1, 1, 1).to(x0.device)
eps = torch.randn_like(x0)
return a.sqrt() * x0 + (1 - a).sqrt() * eps, eps
def train():
dev = "cuda" if torch.cuda.is_available() else "cpu"
ds = datasets.MNIST("data", train=True, download=True,
transform=transforms.Compose([transforms.Pad(2),
transforms.ToTensor(), transforms.Lambda(lambda x: x * 2 - 1)]))
dl = DataLoader(ds, batch_size=128, shuffle=True, num_workers=2, drop_last=True)
net = UNet().to(dev); opt = torch.optim.AdamW(net.parameters(), 2e-4)
for ep in range(8):
for x0, _ in dl:
x0 = x0.to(dev)
t = torch.randint(0, T, (x0.size(0),), device=dev)
xt, eps = add_noise(x0, t)
loss = F.mse_loss(net(xt, t), eps)
opt.zero_grad(set_to_none=True); loss.backward()
torch.nn.utils.clip_grad_norm_(net.parameters(), 1.0); opt.step()
print(f"ep{ep} loss={loss.item():.4f}")
torch.save(net.state_dict(), "ddpm.pt")
@torch.no_grad()
def sample(n=64, ckpt="ddpm.pt"):
dev = "cuda" if torch.cuda.is_available() else "cpu"
net = UNet().to(dev); net.load_state_dict(torch.load(ckpt, map_location=dev)); net.eval()
x = torch.randn(n, 1, 32, 32, device=dev)
for t in reversed(range(T)):
tt = torch.full((n,), t, device=dev)
eps = net(x, tt)
a, ab, b = alphas[t].to(dev), abar[t].to(dev), betas[t].to(dev)
x = (x - (1 - a) / (1 - ab).sqrt() * eps) / a.sqrt()
if t > 0: x = x + b.sqrt() * torch.randn_like(x)
utils.save_image((x.clamp(-1, 1) + 1) / 2, "samples.png", nrow=8)
print("saved samples.png")
if __name__ == "__main__":
import sys
train() if len(sys.argv) < 2 or sys.argv[1] == "train" else sample()4.3 采样器与 Classifier-Free Guidance
本章目标:搞清”同样的模型,为什么有人 20 步出图有人 1000 步”,以及 CFG 这个”特效药”为什么是文生图质量的一半功劳。学完标准:能给采样器分类并按场景选用,能手写 DDIM,能推导 CFG 并说清 guidance scale 的 trade-off。
1. 采样的另一面:解一条反向轨迹
4.2 的采样循环( ancestral/DDPM 采样)是马尔可夫链逐步走,1000 步、带随机性。后续研究的洞察:加噪-去噪过程其实对应一条连续时间的概率流 ODE/SDE——采样就是在解这条方程。一旦看成 ODE,两件事立刻打开:① 数值分析百年的 ODE 求解器随便用(步长可以很大);② 轨迹可以确定性(同一噪声同一图)。“采样慢”从物理约束变成了数值方法问题——这就是 4.1 说的”蒸馏与流把迭代变快”的理论入口。
2. 采样器动物园(按思想分类)
| 类别 | 代表 | 步数 | 特点 |
|---|---|---|---|
| 祖先采样(SDE) | DDPM | 1000 | 每步加噪,随机、多样 |
| 去噪扩散隐式模型 | DDIM | 20–50 | 去掉过程噪声假设,可跳步、确定性 |
| 高阶 ODE 求解器 | DPM-Solver++、UniPC | 10–25 | 利用轨迹曲率,指数积分,工业默认 |
| 一致性/蒸馏 | LCM、Turbo 系 | 1–4 | 蒸馏轨迹(把多步压成少步),质量略降 |
选用心法:要多样性/探索 → DDPM/DDIM-ancestral;要快而稳 → DPM-Solver++ 20 步;要实时 → 蒸馏系。diffusers 里就是 scheduler 一个参数的差别——同一权重配不同调度器是合法操作(这提醒你:模型和采样在数学上是解耦的两层)。
DDIM 手写(作业核心,~20 行)
DDIM 更新式:
读法:先用模型隐式猜出原图 ,再直接跳到目标时刻的加噪版本——跳多少步随你(子序列采样)。在 4.2 的 MNIST 模型上实现它,500 步 → 20 步对比。
3. CFG:无分类器引导(文生图的特效药)
问题:怎么让模型听话?经典方案是训练一个分类器给梯度引导(classifier guidance)——要额外训分类器、且在扩散的噪声图上做分类很别扭。CFG(Ho & Salimans, 2022)把它整个扔掉:
训练:条件生成时以约 10% 概率把条件丢弃(置空)——同一个网络同时学会 和 。
采样:把”有条件方向”减去”无条件方向”,再放大 s 倍:
直觉: 是”条件带来的修正方向”,s 是对它的放大器。s=1 退回普通条件生成;s=5~8(SD 常用 7)图更贴 prompt、对比更强;s 过大 → 过饱和、僵硬、“塑料感”(分布被推到训练数据之外)。CFG 是”训练时埋伏笔、推理时调旋钮”的设计典范——这种”一次训练、推理可控”的思路在 RL 的 KL 系数(2.7)、美学引导(8.2)里反复出现。
工程衍生:负 prompt 就是把 换成”你不想出现的东西”(模糊、多指、水印);CFG 蒸馏(guidance distillation)把 s>1 的效果直接蒸进模型,省掉每步的两次前向(Turbo/LCM 的组件之一)。
4. 自测题
- 把采样看成 ODE 带来哪两个立即收益?(大步长求解器;确定性轨迹)
- DDIM 跳步的数学勇气在哪?(放弃马尔可夫假设——只要求端点分布一致,中间路径自由)
- CFG 训练时丢弃条件的目的是什么?(同一网络内同时学到条件与无条件两个模型)
- guidance scale 的物理直觉与过量的症状?(条件修正方向的放大器;过饱和/塑料感)
- 负 prompt 在公式里对应哪一项?(把 ε_∅ 替换为负条件嵌入——同一公式的工程化用法)
- 为什么说”模型与采样器解耦”?(同一权重可配任意 scheduler——训练学的是 score/速度场,采样是数值积分方式的选择)
5. 动手作业
- 在 4.2 的 MNIST 模型上实现 DDIM(跳步 500→20/50/100 三档),同一起点噪声对比确定性输出;
- 接
diffusers跑 SD1.5,固定 seed 扫 guidance_scale = 1/3/7/15 四档,用 8.1 的语言写”过量症状”观察笔记; - 实现负 prompt(SD 管线
negative_prompt参数),构造一组”负向救图”的对照案例; - 挑战:读一致性模型(LCM)论文 §1,用三句话讲清”蒸馏轨迹”和”蒸馏 CFG”分别压缩了什么成本。
案例 · 手算:DDIM 一步跳采样
案例:从 t 到 t−1 只用三行算术
设当前 ,模型预测 ;schedule 给 (),目标时刻 ()。
- 隐式预测原图:
- 直接跳到目标时刻:
注意 DDIM 这步没有加随机噪声(确定性轨迹)——同一 x_t 永远到同一 x_{t−1}。跳步的本质就藏在第 1 行:先”猜出”原图,再把它按目标时刻重新加噪——中间的马尔可夫链被整个跳过了。4.2 作业里你会在自己的 MNIST 模型上验证:500 步的链,20 步跳完质量只掉一点点。
6. 延伸资源
- DDIM 论文 / CFG 论文(Classifier-Free Diffusion Guidance)——各十分钟读完
- DPM-Solver 论文 §1——ODE 视角的科普级开头
- diffusers 文档 Schedulers 页——把动物园点一遍名
4.4 Latent Diffusion 与 Stable Diffusion:生成模型工程学
本章目标:拆解 SD 的三大件(VAE 压缩器 / U-Net 去噪器 / 文本编码器),理解”在潜空间做扩散”这个工程决策如何改变了整个行业。学完标准:能画出 SD 推理的完整数据流,知道 LoRA/ControlNet 挂在哪,能解释 SD1.5→SDXL→SD3 的升级逻辑。
1. 核心决策:像素太贵,先压缩再扩散
512×512×3 的图像直接做扩散,每步注意力都在百万级像素上算——训练成本天文数字。Latent Diffusion(Rombach et al., 2022)的洞察:感知上无信息的大量像素,先压掉再扩散:
扩散的加噪、去噪、采样全部发生在 64×64 的潜空间,最后 VAE 解码器一步还原。为什么敢这么做:VAE 学到的潜码保留了”感知必要”的信息(4.1 说的 VAE 还魂——它不做生成,只做压缩/解压)。“LDM = VAE 压缩器 + 潜空间扩散模型 + 文本条件注入”,这个三段式是整个开源文生图生态的地基。
2. 三大件逐个拆
2.1 VAE:KL-f8 自动编码器
编码/解码各是一个卷积网络,潜码 4 通道、空间各 ÷8(f8)。训练用重建+KL+感知损失(3.4 VQ-VAE 同款工具箱的连续版)。你实际用它的地方:SD 一切微调(LoRA/ControlNet)都冻结 VAE——动它就会”编码-解码不对齐”;偶尔见的”SD 图发灰/细节糊”,一半嫌疑在 VAE 版本不匹配。
2.2 U-Net:带交叉注意力的去噪器
1.1 §5 埋过线:U-Net = 编码器(下采样提语义)+ 解码器(上采样还细节)+ 跳跃连接(把编码器各分辨率的特征直接接给解码器——空间细节不用挤过瓶颈)。SD 的 U-Net 加了关键一层:在若干分辨率上插入 cross-attention,其中 Q 来自图像特征、K/V 来自文本嵌入(1.2 章的 cross-attention 原样登场)——这就是”文生图的条件注入机制”本体:文本通过 K/V 决定”每个空间位置该注意文本里的哪些词”。
时间步 t 的注入则用 adaLN/调制方式(scale/shift 特征归一化参数——4.5 的 DiT 会把这个手法用到极致)。
2.3 文本编码器:CLIP text encoder
prompt 先过 CLIP 文本塔(1.6 的老朋友)得到 77×768 嵌入,再喂给 U-Net 的 cross-attention K/V。这就是”CLIP 分数过滤训练数据 + CLIP 编码 prompt”的双料地基(8.2 的伏笔:文本编码器的语义空间质量直接封顶”模型对 prompt 的理解力”)。
3. 推理数据流(画得出才算懂)
prompt → CLIP 文本塔 → 文本嵌入 (77,768) ─┐
├→ U-Net ×20步(DPM-Solver,潜空间) → 潜码 64×64×4 → VAE 解码 → 图
随机噪声 (64,64,4) ────────────────────────┘ ↑ CFG 每步条件/无条件两次前向 (4.3)
diffusers 实操(10 行):
from diffusers import StableDiffusionPipeline
import torch
pipe = StableDiffusionPipeline.from_pretrained(
"stable-diffusion-v1-5/stable-diffusion-v1-5", torch_dtype=torch.float16).to("cuda")
img = pipe("an impressionist oil painting of Hangzhou West Lake",
negative_prompt="blurry, low quality",
guidance_scale=7, num_inference_steps=25).images[0]
结构自检:这 10 行里,你能指出 VAE 在哪(pipeline 内部首尾)、U-Net 在哪(循环体)、CLIP 在哪(prompt 编码)、CFG 在哪(guidance_scale)、采样器在哪(25 步循环)吗?说不出的回去翻 §3。
4. 谱系与升级逻辑
- SD1.5(2022):f8 VAE + CLIP ViT-L + 860M U-Net,256² 训练 512² 微调——生态爆发(LoRA/ControlNet 全长在它身上);
- SDXL(2023):更大 U-Net(2.6B)+ 双文本塔(CLIP×2)+ 宽高比分桶训练(告别方图偏执)+ Refiner 两段式;
- SD3 / FLUX(2024–):U-Net 换成 DiT/MMDiT(Transformer),DDPM 换成 Flow Matching——下一章的主角,架构与目标双双现代化。
升级逻辑一句话:压缩器稳定不动(VAE 几乎没换代),去噪器从 CNN 走向 Transformer,训练目标从 ε-MSE 走向流匹配,文本理解从单 CLIP 走向多编码器。看懂 SD 的换代,就看懂了生成模型工程学的半部历史。
5. 自测题
- LDM 的压缩比是多少?为什么敢在潜空间扩散?(48 倍;VAE 保住了感知必要信息,扩散只负责”结构”不负责”像素”)
- 文本条件注入的机制本体是什么?(U-Net 里的 cross-attention:图像做 Q、文本嵌入做 K/V)
- 为什么 LoRA/ControlNet 微调都冻结 VAE?(编码-解码一致性被破坏则全链路漂移)
- 跳跃连接解决什么问题?扩散 U-Net 里它还重要吗?(下采样丢的空间细节直通解码器;重要——细节重建全靠它)
- SDXL 相比 1.5 的四处升级?(大 U-Net/双文本塔/分桶/Refiner)
- SD3 换掉的是哪两个组件?(U-Net→DiT;DDPM→Flow Matching)
6. 动手作业
- 跑通 §3 的 10 行;把
output_type="latent"拿到潜码,vae.decode前先可视化它(reshape 成 4 通道热力图)——亲眼看看”扩散画布”长什么样; - 逐行读
diffusers的StableDiffusionPipeline.__call__源码,把 §3 数据流的每个箭头对上代码行; - 换 scheduler 实验:同一 prompt/seed 用 DDIM 50 步 vs DPM-Solver++ 20 步 vs LCM 4 步,三图对比;
- 挑战:潜码上手动加 10% 噪声再解码,观察哪类信息先坏(通常高频纹理先崩)——体会”潜码保结构、VAE 保质感”的分工。
图解 · SD 推理全链路(Mermaid 版)
flowchart LR
P["prompt"] --> T["CLIP 文本塔"] --> E["文本嵌入 (77×768)"]
N["随机噪声<br>64×64×4 潜码"] --> U["U-Net 去噪 ×20 步<br>(DPM-Solver)"]
E --> U
U -. "CFG:每步条件/无条件<br>两次前向(4.3)" .-> U
U --> L["干净潜码 64×64×4"]
L --> V["VAE 解码器(f8)"] --> IMG["512×512 图像"]三个”到此一游”的老朋友:CLIP 文本塔(1.6)、cross-attention 注入(1.2 的 K/V 机制,在 U-Net 内部)、CFG(4.3)。SD 的推理不是新技术,是全书前半部分零件的一次总装——这也是为什么”看懂 SD”被当作多模态学习的中期检核点。
7. 延伸资源
- LDM 论文(High-Resolution Image Synthesis with Latent Diffusion Models)
- Hugging Face Diffusers 文档《Stable Diffusion 入门》——工程视角
- SDXL / SD3 技术报告——换代逻辑的一手材料
4.5 DiT 与 Flow Matching:生成模型的现代化
本章目标:讲清当前最先进文生图/视频生成(SD3/FLUX/可灵/Sora 类)的两个共同底座——DiT 架构与 Flow Matching 训练目标。学完标准:能解释”扩散也可以是 Transformer”和”直线搬运为什么又简单又好”,并把 DDPM→Flow 的演化线完整串起来(卷4 的收官钥匙)。
1. DiT:把 U-Net 换成 Transformer
DiT(Peebles & Xie, 2023)做的事情简单到一句话:潜码 patch 化成 token 序列,用标准 Transformer(ViT 骨架)当去噪器。64×64×4 的潜码按 2×2 patch 切成 1024 个 token——从此生成模型和 LLM 共享同一套架构与工程栈(FlashAttention、FSDP、scaling law 全部平移可用)。
条件注入的关键设计:adaLN-Zero——t 和类别/文本条件不拼进输入,而是回归出每个 block 里 norm 层的 scale/shift/gate 参数(调制式注入,4.4 埋过线);gate 初始化为零,每个 block 从”恒等”出发——和 LoRA 的 B 置零(2.6)、Flamingo 的零门控(3.3)同一个哲学第三次出现:新模块不破坏预训练行为。
为什么 Transformer 赢了:
- scaling 表现更好——同等算力下 DiT 的 FID 随模型增大稳定下降(论文的 scaling 曲线是它中选 Sora 架构的直接原因);
- 与多模态天然兼容——文本/图像/视频都是 token,一套架构吃所有模态(Sora 的 spacetime patch:把时空块统一 token 化);
- 工程复利——LLM 侧的一切加速/分布式技术直接搬过来。
U-Net 没有死(小模型/端侧仍用它),但前沿大模型全面 Transformer 化。FLUX/SD3 的 MMDiT 更进一步:文本和图像各有一条数据流(各自的 QKV),在 attention 内部拼接交互——专为”两种模态地位对等”设计的双流结构。
2. Flow Matching:训练目标的最简化
DDPM 的装备清单:β schedule、ᾱ 闭式表、 ancestral 链、各种修正(cosine schedule、v-pred…)。Flow Matching(Lipman et al., 2023,及同期的 Rectified Flow)把这一切换成一条直线:
路径定义:数据 和噪声 之间走直线插值:
学习目标:网络 预测这条直线上的速度:
采样:从噪声 出发解 ODE ,欧拉法走 N 步到 。
为什么好:
- 无 schedule 无超参——没有 β 表、没有噪声约定,训练就一个 MSE;
- 路径直 → 采样快——DDPM 的概率流轨迹弯曲(要小步走),直线轨迹欧拉法十几步就走完。Rectified Flow 的 Reflow 还能把轨迹进一步拉直(走向 1-step 生成的理论通道);
- 理论干净——它就是连续归一化流(CNF)的免模拟训练法,likelihood 可算。
和 DDPM 的关系(卷4 收官的一笔画):两者同属”构造一条噪声↔数据的插值路径 + 学沿路径的速度/去噪方向”的大家族——DDPM 选了”马尔可夫加噪的弯曲路径”,Flow 选了”直线”。ε-pred、v-pred、velocity 本是同一种”方向场”在不同路径参数化下的名字(4.2 §5 的伏笔在此收线)。数学上殊途同归,工程上直线更省步数——这就是 SD3/FLUX 全面转向 Flow Matching 的全部理由。
3. 实操:在 diffusers 里摸到两者
# FLUX / SD3 管线:架构与目标都是新一代
from diffusers import FluxPipeline
pipe = FluxPipeline.from_pretrained("black-forest-labs/FLUX.1-schnell",
torch_dtype=torch.bfloat16).to("cuda")
img = pipe("a cyberpunk street food stall in Chengdu, night, neon",
num_inference_steps=4, guidance_scale=0.0).images[0] # schnell:4 步蒸馏
对照观察:SD1.5(U-Net+DDPM,25 步+CFG=50 次前向)vs FLUX-schnell(DiT+Flow 蒸馏,4 步 0 CFG)——架构现代化+目标简化+蒸馏的三重红利就摆在两张图的耗时里。学术开源:RectifiedFlow、flow-matching(Meta)库有完整训练代码,MNIST 级复现作业见下。
4. 自测题
- DiT 怎么处理潜码?条件怎么注入?(2×2 patch → 1024 token;adaLN-Zero 调制 norm 参数,gate 零初始化)
- “零初始化哲学”三连是哪三处?(Flamingo 门控 / LoRA B 置零 / DiT adaLN-Zero——新模块从恒等出发)
- Flow Matching 的训练对是什么?loss 是什么?(;速度场 MSE)
- 直线路径为什么采样快?(欧拉法对直线积分误差小——十几步即可;弯曲路径需要小步)
- MMDiT 的”双流”设计为哪个问题而生?(文本与图像模态地位对等、各自保有自己的表示流再交互)
- 一句话总结 DDPM→Flow 的演化?(同一家族内:把”路径”从弯曲的马尔可夫加噪换成直线插值,训练更简、采样更省步)
5. 动手作业
- 用 Meta
flow_matching库(或手写 30 行)在 MNIST 上训练一个 rectified flow,对比你 4.2 的 DDPM:同预算训练下 10 步采样的质量差——亲手验证”直线更快”; - 画出同一样本在 DDPM 与 RF 下的 ODE 轨迹(取 3 个中间点投影到二维)——亲眼看”弯 vs 直”;
- 跑 FLUX-schnell 4 步 vs SD1.5 25 步,统计两张卡上的耗时与显存,写一段”现代化红利”笔记;
- 挑战:读 Reflow 论文 §1,解释”把 (x1, x0) 配对重训一遍为什么能进一步拉直轨迹、通向 1-step 生成”。
案例 · 数值:一条直线上的速度与欧拉步
案例:为什么直线路径两步就到家
一维情形:数据 ,噪声 。路径 。
解析速度:,沿整条路径是常数——“直线”的数学含义。
训练目标演示:任取 → ;网络要从 预测出 0.8(DDPM 里这个角色是 ε,这里换成速度,任务同构)。
两步欧拉采样验证:从 出发、步长 0.5: → ✓ 两步精确到家。
对照:DDPM 的弯曲路径同样两步欧拉会差得很远(曲率让每步都引入偏差)——4.5 正文”直线省步数”的定量演示,也是 SD3/FLUX 能十几步出图的数学原因。
6. 延伸资源
- DiT 论文(Scalable Diffusion Models with Transformers)——重点看 scaling 曲线
- Rectified Flow / Flow Matching 论文——二选一精读(数学几乎同构)
- SD3 论文(Rectified Flow 版)——工业界如何选路径与采样器的完整实验记录
4.6 可控生成:ControlNet、IP-Adapter 与风格 LoRA
本章目标:掌握”prompt 之外的控制手段”——空间控制(ControlNet)、参考控制(IP-Adapter)、风格控制(LoRA),并落到美术学工作流。这是卷4 与你导师方向连接最紧的一章。学完标准:能说清三种控制各自”控制什么、怎么注入”,并跑通至少一种的微调。
1. 问题:prompt 是粗粒度遥控器
4.3 的 CFG 控制”画什么”,但对构图、姿态、线稿、颜色分布这些形式层(8.1)的表达力很弱——文字说”三分法构图”模型多半不理你。三类更强控制,对应三种信息注入位置:
| 手段 | 控制什么 | 注入位置 | 成本 |
|---|---|---|---|
| LoRA | 风格/概念/人物 | 微调权重本体(2.6 同款技术) | 数十张图即可 |
| ControlNet | 空间结构(边缘/深度/姿态/线稿) | 额外旁路编码器,逐层注入 | 需成对数据训练 |
| IP-Adapter | 参考图的内容/风格/身份 | 文本 K/V 之外的独立图像 K/V | 轻量训练 |
2. 风格 LoRA:美术方向的第一件兵器
2.6 的 LoRA 原理原样搬到扩散模型(挂 U-Net 或 DiT 的 attention 投影),差异只在数据和验收:
- 数据:某画家的 30–200 张高清图(WikiArt 按作者抓取),统一裁剪分辨率;caption 要小心——全部用”by artist XXX”式的占位 caption,把风格”锁”进触发词,防止画风和内容语义纠缠;
- 训练:SD1.5/SDXL 上 rank 8–32、lr 1e-4、2000–5000 步(diffusers 的
train_text_to_image_lora或 kohya 脚本);4090 上一小时量级; - 验收(美术方向的特色):不只看”像不像”,用 8.1 的语言分层验收——色相分布是否复现(算直方图对比)、笔触肌理是否在、明暗对比性格是否保持。“风格复现度”本身就能做成量化评测——这是论文点(8.7 的伏笔);
- 伦理红线:在世艺术家风格 LoRA 有权利争议(8.1 §9),研究用已故大师+公开数据集,论文里写清数据来源与用途限定。
3. ControlNet:让结构听你的
设计:把预训练模型的一部分(SD U-Net 的下采样/中间块)复制一份作为可训练旁路;控制信号(Canny 边缘、深度图、人体姿态、线稿)过这份副本,逐层” injecting”回主干——两处零卷积(zero-conv)连接(1×1 卷积、权重与偏置初始化为 0):训练起点旁路输出恒为零,主干行为与原模型完全一致。“零初始化哲学”第四次出现(Flamingo 门控/LoRA B 置零/DiT adaLN-Zero/ControlNet zero-conv)——这个模式值得你写进自己的科研直觉:给预训练模型加任何新能力,都从”不干扰原行为”的起点出发。
训练数据:成对(控制图, 图文对)——用现成大模型的深度/边缘估计从海量图文对”自动制造”控制图(弱监督自举,5 百万对级别)。思考题:这本质是”用旧模型给新模型造监督”——和你将来蒸馏/数据引擎的思路同源。
美术工作流:线稿上色(lineart ControlNet + 风格 LoRA 叠加——控制来自画师线稿、风格来自 LoRA,两者正交可叠加)、构图迁移(depth)、名画构图重绘(pose+composition)。叠用规则:多个 ControlNet 权重配比(controlnet_conditioning_scale 0.5–1.0)调平衡。
4. IP-Adapter 与图像编辑的现代化
- IP-Adapter:给 U-Net 的 cross-attention 解耦出第二组 K/V 投影专接图像特征(CLIP image encoder 编码参考图)——文本说”画什么”,参考图说”长什么样/什么风格”。训练只动这组新投影(~22M 参数), Again 是”旁路+轻量”模式;
- 趋势(2025–2026):控制正在从”显式地图”走向”指令编辑”——FLUX Kontext、Qwen-Image-Edit、StepOCR 类模型用一句话完成”把背景换成黄昏/保持人物改画风”,本质是多图输入的 DiT(参考图作为条件 token 进 MMDiT)。但美术工作流里显式控制(线稿/色块/深度)并未过时——它给的精确性是语言给不了的;你的研究空间恰在”指令编辑的美术专业版”(比如”按宋代院体规范改线”)。
5. 自测题
- 三种控制手段分别控制什么层?(风格概念→权重;空间结构→旁路逐层注入;参考内容→解耦图像 K/V)
- zero-conv 的作用?哪三次前例共享此哲学?(训练起点旁路为零、不扰动原模型;Flamingo/LoRA/DiT——“零初始化哲学”)
- 风格 LoRA 的 caption 为什么要用占位触发词?(把风格锁进触发词,防止与内容语义纠缠——“style leakage”防治)
- ControlNet 的控制图哪来的?(预训练估计器从图文对自动制造——弱监督自举)
- IP-Adapter “解耦”的是什么?(文本 K/V 与图像 K/V 分开投影,正交可控可加权)
- 指令编辑模型兴起后,显式控制在美术场景为何仍不可替代?(线稿/色块/构图的精确性语言无法表达——专业创作需要像素级控制)
6. 动手作业(美术方向试金石)
- 从 WikiArt 取莫奈(或你与导师商定画家)80 张,训一个风格 LoRA;生成 20 张图,与真迹对比:色相直方图 JS 散度 + 主观打分两张表——你的第一个”风格复现度量化”实验;
- 用 lineart ControlNet:把一幅素描线稿分别用”莫奈 LoRA”和”浮世绘 LoRA”上色,同构图不同风格——叠用系统跑通;
- IP-Adapter:拿一幅真迹当参考,生成同风格新题材,评估”风格迁移 vs 内容泄漏”的边界(写 200 字);
- 全部实验记录进 repo,起名
art-control-suite——8.7(艺术基准构建)的雏形。
7. 延伸资源
- ControlNet 论文(Zhang et al., 2023)——zero-conv 与自举数据两处精华
- IP-Adapter 论文——解耦 cross-attention
- diffusers 文档 ControlNet/LoRA 训练页——工程直达
4.7 视频生成:Sora 范式与开源阵营
本章目标:把视频生成这条”产业最凶”的赛道讲成一张技术地图——3D VAE、时空 token、DiT 缩放,开源阵营现状,以及视频生成向世界模型的合流(本笔记开篇判断的兑现)。学完标准:能画出视频生成的技术栈,说清”视频 DiT 比图像 DiT 多了什么”,知道学生在哪里下手。
1. 从图像到视频:多了什么
视频 = 图像 + 时间一致性。三个新问题:① 时间维的数据量爆炸(16 帧 1080p ≈ 上亿像素);② 帧间要运动合理(物理、遮挡、视角变化);③ 长视频要时间连贯(漂移、遗忘)。对应的三个技术件:
- 3D 因果 VAE:把时空一起压缩(空间 ÷8,时间 ÷4 级别),“因果”指每帧只依赖过去帧——适合流式;
- 时空 token 化:压缩后的 latent 按 3D patch(时空块)切成 token 序列——Sora 的 spacetime patch 就是图像 patch(1.4)的直接推广,Transformer 对”一切皆 token”的普适性在此封神;
- DiT + Flow Matching 平移:4.5 的整套架构与训练目标原样搬到 token 序列上,规模加大(Sora 级模型数十 B 参数)。
Sora 技术报告(2024)的历史地位:证明了”视频生成 = token 上的 scaling law”——质量随算力平滑提升、涌现出 3D 一致性与物体持久性。它把视频从”GAN 时代的鬼畜”一举拉到”潜在世界模拟器”的叙事,整个产业随之转向。
2. 开源与产业阵营(2026 快照)
| 阵营 | 代表 | 特点 |
|---|---|---|
| 商业闭源 | Sora 2(音视频联合)、可灵(快手)、Veo(Google)、即梦 | 质量/物理合理性标杆,生态收费 |
| 开源旗舰 | HunyuanVideo(腾讯)、Wan2.x(阿里)、CogVideoX(智谱) | 14B/13B 级 DiT,LoRA/Control 生态活跃 |
| 轻量高效 | LTX-Video、Mochi | 消费级卡实时/准实时,端侧路线 |
开源动手建议:Wan/Hunyuan 的 LoRA 微调与 Control 生态最活跃(4090 可玩 LoRA 级);CogVideoX 2B 级可全参 LoRA。训练基础模型是巨头的事,后训练与控制是你的事——与图像生成(4.6)完全同构的分工。
3. 合流:视频生成 → 世界模型
本笔记卷首的判断在此收线:视频模型正在被重新定位为世界模型/物理模拟器——不只生成”好看的视频”,而是作为机器人训练环境(5.3 VLA 的仿真数据源)、物理合理性评测对象。技术证据链:后训练对物理一致性的强化(物体不穿模、液体不倒流)、物理先验注入(RoboScape 类物理知情世界模型)、以及”生成式数据引擎”给具身供数。这是你论文选题里”故事最完整”的一条线:视频生成(4.x)× 具身(5.3)× 世界模型(5.4)三卷在此握手。
4. 学生可做的四个方向(算力友好)
- 视频 LoRA/风格化:Wan 系 + 4090,画风/角色一致性微调(美术方向的 B 线延伸——“让画动起来”);
- 物理一致性评测:构建”物理违规检测”基准(穿模/重力反常/因果颠倒)——VBench 类工作之外,领域化物理评测仍稀缺(A 线思路);
- 运动可控生成:轨迹控制、首末帧插值、相机路径控制的 LoRA/adapter 研究;
- 视频理解侧的反向题:给 VLM 配视频输入做”物理常识问答”(3.5 的 Qwen 系长视频能力)——生成与理解在此互为评测。
5. 自测题
- 视频生成比图像多了哪三个技术件?(3D 因果 VAE / 时空 token 化 / DiT+Flow 的规模平移)
- spacetime patch 与 ViT patch 的关系?(同一思想在三维的直接推广——“一切皆 token”)
- Sora 报告改变行业叙事的一句话是什么?(视频 = token 上的 scaling law = 潜在世界模拟器)
- 为什么说”后训练与控制是学生的分工”?(基础模型训练是亿级卡时;LoRA/Control/评测单卡可做且是产业刚需)
- 视频→世界模型合流的证据链三条?(物理一致性后训练/物理知情模型/具身数据引擎)
- 你的 A 线评测思路在视频里怎么落?(物理违规检测基准——领域化评测的稀缺位)
6. 动手作业
- 用 diffusers 跑 CogVideoX-2B(或 LTX)出 3 段视频,记录单卡耗时与显存——建立”视频生成的算力手感”;
- 跑 VBench 的开源评测(或其子集)对一个开源模型出分——见识视频评测的维度设计;
- 挑战:给 Wan 系开源模型训一个 500 步的画风 LoRA(用你 8.3 的画家数据集),观察”图像风格如何影响运动质感”——这是 B 线选题的一手素材。
7. 延伸资源
- Sora 技术报告(OpenAI, 2024)——范式宣言,20 分钟读完
- HunyuanVideo / Wan2.1 技术报告——开源阵营的架构细节
- VBench 论文——视频评测的维度体系
4.8 统一模型之争:Chameleon、Transfusion、Janus
本章目标:讲清”一个模型既理解又生成”的三条架构路线及其取舍——这是 4.x 的收官章,也是多模态领域最重要的一场架构辩论。学完标准:能画出三条路线的结构图,说清各自的天花板,理解为什么 DeepSeek 的”解耦”是务实的赢家。
1. 圣杯问题
GPT 能理解图像(接上视觉塔,卷3)却不能画图;SD 能画图却不会聊天(4.x)。统一模型的愿景:一套权重,看图说话、听话作图、图文交错推理——就像人。三种路线,三种哲学:
2. 路线一:Chameleon——全离散,一套目标走天下
Meta(2024)的激进方案:文本 token + VQ 图像 token(3.4)进同一个词表,单一 Transformer 纯自回归——理解和生成都是 next-token prediction,目标完全统一。
两个代价:① 训练不稳——两种模态的数值分布差异大导致 norm 发散,Chameleon 为此发明了 QK-Norm(2.3 埋过线的稳定件,后来被 Qwen3 等广泛继承——统一模型的副产品反哺了 LLM);② 生成质量被 VQ tokenizer 封顶(3.4 的天花板定律):Chameleon 的图约 1M token 的重建精度,明显落后同期专用扩散模型。
哲学:统一性 > 短期质量。赌的是”Scaling law 会填补差距”。
3. 路线二:Transfusion——一套 Transformer,两种损失
Meta 的折中(2024):图像不走离散 token,而是连续 latent 混在序列里;训练时混合目标——文本 token 用 LM 损失,图像片段用扩散损失(对这段序列做去噪)。注意力对全序列统一计算,模态间深度交互。
取舍:避开了 VQ 天花板(图像质量对齐扩散模型);代价是训练复杂度高(两种损失的平衡、噪声调度混进序列)、推理时生成要走多步扩散循环,“一个目标”的优雅性打折。
4. 路线三:Janus——解耦视觉编码,务实者的胜利
DeepSeek(2024–25)问了一个 3.4 章早就埋下的问题:为什么要让一个视觉编码器同时伺候两个主人? 理解要的是语义特征(SigLIP 式),生成要的是细节重建(VQ 式)——两者天然冲突。Janus 的答案:编码器解耦、主干共享——SigLIP 编码”看”,VQ tokenizer 编码”画”,两路特征都进同一个 LLM 主干,自回归统一输出。
结果:Janus-Pro 以更小的规模在理解与生成两边同时打过 Chameleon——“解耦”证明了”统一”不等于”同一套编码”。这是工程哲学对架构洁癖的又一次胜利(与 LLaVA 的 MLP 胜 Q-Former 同款剧情)。
5. 三路线对照表(背下来)
| Chameleon | Transfusion | Janus(-Pro) | |
|---|---|---|---|
| 图像表示 | 离散 VQ token | 连续 latent | 双编码器(语义+VQ) |
| 训练目标 | 纯自回归 | LM+扩散混合 | 纯自回归(两组编码) |
| 天花板 | VQ 重建质量 | 训练复杂度 | 双编码器的算力开销 |
| 训练稳定性 | 差(QK-Norm 救场) | 中 | 好 |
| 一句话哲学 | 统一性至上 | 质量与统一的折中 | 解耦冲突,务实优先 |
2026 的现状:没有单一赢家,但收敛方向清晰——理解侧向 early-fusion 走(Qwen3-VL),生成侧向 Flow/DiT 走(4.5),统一模型研究聚焦”怎么把两者塞进一套权重”(Transfusion 变体与解耦路线是主流)。对学生的意义:统一模型的基础研究门槛高,但评测(统一模型的图文能力冲突量化)、tokenizer(3.4 的续作)、模态冲突的可解释性都是开放题。
6. 自测题
- Chameleon 的两大代价及其一个副产品?(VQ 封顶、训练不稳;QK-Norm 反哺 LLM)
- Transfusion 的”混合”具体指什么?(同一序列里文本走 LM 损失、图像 latent 走扩散损失)
- Janus 解耦的理由?为什么说是”务实”?(理解与生成对视觉特征的需求冲突;双编码器小成本换两边性能)
- 3.4 的哪条洞察预言了 Janus?(tokenizer 天花板 + 理解要语义/生成要细节的分工)
- 统一模型”没有单一赢家但收敛清晰”指什么?(理解 early-fusion 化、生成 Flow 化、架构辩论聚焦编码方式)
7. 动手作业
- 画三路线结构图(手绘即可),在每条线上标注”编码方式/训练目标/天花板”三要素;
- 用 Janus-Pro(或 Chameleon)开源权重各生成 5 张图 + 问 5 个理解题,与同尺寸专用模型(SD+Qwen-VL)对比——建立”统一 vs 专用”的手感差距;
- 精读 Janus-Pro 技术报告的消融部分:找”解耦 vs 共享编码器”的对照数据;
- 挑战:列出统一模型的三个未解问题(提示:tokenizer 上限、训练稳定性、图文干扰)——每个都是 6.3 的选题候选。
8. 延伸资源
- Chameleon / Transfusion(Meta 技术报告)——路线一与路线二的原始宣言
- Janus / Janus-Pro(DeepSeek)——路线三,精读消融
- Show-o / Emu3——混合与全离散的后续演化(泛读)
4.9 前沿瞭望:扩散语言模型
本章定位:卷4 的收官章——当生成模型的方法论反过来入侵 LLM 的地盘会怎样?了解扩散语言模型(Diffusion LM)的机制、优势与现状,建立”自回归不是唯一的生成范式”的免疫。学完标准:能讲清掩码扩散并行解码的机制,能列出它与 AR 的真实差距。
1. 动机:AR 的三个先天限制
卷2 你已把自回归焊死在脑子里(causal mask + 逐 token 生成,2.3),现在看它的三处”先天性”:
- 串行生成:token 一个接一个出——速度被链长锁死(2.8 的 decode memory-bound 之上再叠串行);
- 单向上下文:生成第 t 个 token 时看不到未来——改一个前缀要全部重写;
- 错误累积:前面的错被后面”将错就错”。
扩散语言模型的赌注:用”从噪声文本迭代去噪”替换自回归——整段文本并行生成,可双向上下文、可任意位置修改。
2. 机制:掩码扩散(主流形态)
现代扩散 LM(MDLM/LLaDA 系)的形态比连续扩散更简洁:
- 前向:随机把文本的一些 token 替换成
[MASK](掩码率随时间 t 变化)——1.5 章 MAE 的文字版; - 训练:让模型在被掩码位置并行预测原始 token(交叉熵);
- 生成:从全
[MASK]序列开始,迭代地”揭示”位置——每轮模型同时预测所有位置,按置信度解码一部分,剩余继续掩码迭代。
与 AR 的本质区别:AR 是”从左到右一条链”,扩散是”从模糊到清晰的整段雕塑”——没有因果 mask 的位置限制,每个位置都能看见全局(3.2 的 <image> 拼接、1.5 的 MAE、3.4 的离散 token——本笔记的零件在此全部合流)。
3. 现状与真实差距(诚实版)
- 里程碑:LLaDA(2025,8B 扩散 LM)证明扩散路线能 scale 到 LLM 规模且通用能力可用;Mercury/Gemini Diffusion 等商用扩散模型展示数倍生成速度优势(并行解码);代码/填补类任务(双向上下文天然友好)表现出色;
- 真实差距:① 变长生成的控制与效率仍不如 AR 成熟;② KV cache 等 AR 推理优化栈(2.3/2.8)不能直接平移;③ 同等规模下通用基准仍略逊最强 AR 模型;④ 生态(微调框架/agent 集成)是 AR 的天下。
- 合理预期:中短期内 AR 仍是主流,扩散在高吞吐、可编辑、填补式场景先吃下阵地;混合架构(AR 主干 + 扩散局部)是缓和路线。
对学生的意义:这是”范式早期”的典型信号(评价指标未固化、优化栈空白)——评测与效率优化是学生可切入的题(例如:扩散 LM 的 KV 替代物、并行解码的调度策略研究),但要做好”赛道可能不兑现”的风险管理(6.3 的降级思维)。
4. 自测题
- AR 的三个先天限制?(串行/单向/错误累积)
- 掩码扩散的三步机制?它和 MAE 什么关系?(掩码-并行预测-置信度揭示;MAE 的文字版+迭代生成)
- 扩散 LM 的天然优势场景?为什么?(填补/编辑/高吞吐——双向上下文+并行解码)
- 为什么 AR 的推理优化栈不能平移?(KV cache 依赖因果结构——扩散的注意力是双向的)
- “范式早期”的三个信号与学生切入点?(指标未固化/优化栈空白/生态缺失→评测与效率题)
- 混合路线指什么?(AR 主干局部扩散——取两者之长的缓和方案)
5. 动手作业
- 读 LLaDA 报告 §1–2,画”AR vs 扩散”的生成过程对比图(一条链 vs 整段雕塑);
- 用 HuggingFace 上的开源扩散 LM(LLaDA 或更小的复现)做一次”文本填补”实验(中间挖空,看它双向补全)——AR 做不到的事,亲手跑一次;
- 测一次生成吞吐:同参数量 AR vs 扩散模型的 tokens/s——验证”并行”叙事的实感;
- 挑战:读 SEDD 或 MDLM 论文的 loss 推导 §3(选读)——检验你 0.1/4.2 的概率与扩散功底。
6. 延伸资源
- LLaDA 论文(2025)——扩散 LM 的规模证明
- MDLM / SEDD 论文——离散扩散的方法基础
- Mercury(Inception Labs)博客——商用扩散模型的速度叙事
5.1 多模态推理与 RL:当前最热的研究现场
本章目标:进入你未来最可能发表论文的领域——让 VLM”想清楚再说、必要时动手看”。2.7 的 GRPO 在这里全面登场。学完标准:能说出这个领域的三条技术路线、一个学生版复现配方,以及审稿人最关心的三个 open problem。
1. 为什么”理解”之后还要”推理 + RL”
卷3 的 VLM 会看会说,但系统性短板仍在:几何题靠蒙、图表数值算错、需要”再看一眼细节”时不会再看、幻觉随难度上升。两条互补的补强路线,恰好对应 RL 的两种用法:
- 让推理链更长更对(视觉 CoT / R1 范式):R1 式长思考迁移到视觉——模型先输出”我观察到…因此…”的长链,再给答案;
- 让模型”动手看”(thinking with images):把视觉操作(裁剪、放大、框选、调用检测器)作为推理中的工具调用——不是被动看一张图,而是主动获取证据。
两条路线的共同引擎是 RLVR(2.7):多模态任务里存在天然可验证的奖励——几何题对答案、图表题对数值、grounding 对框 IoU、GUI 任务对完成状态。“可验证”从数学/代码平移到视觉,就是这个方向 2024–2026 爆发的直接原因。
2. 三条技术路线与代表作(截至 2026 的格局)
| 路线 | 核心机制 | 代表工作类型 |
|---|---|---|
| 视觉长 CoT + RL | R1 配方平移:冷启动长思考数据 → GRPO | Vision-R1、LLaVA-CoT 类、各家”思考型 VLM” |
| Thinking with images | 工具调用式 RL:裁剪/缩放/grounding 作为动作空间 | DeepEyes、OpenThinkIMG、GUI agent 系 |
| 过程奖励/多粒度验证 | 除最终答案外对中间步骤给奖励 | PRM 类、多 verifier 组合 |
配套的共性组件:数据(GSM8K/ImageNet 几何题/ChartQA 类可验证集);奖励设计(格式奖励保证可解析 + 答案奖励 + 过程/工具奖励);训练栈(Qwen2.5/3-VL 2–7B + LoRA + GRPO,框架 TRL / verl / EasyR1)。
3. 学生版复现配方(把”论文级”降到你的一张卡)
- 任务:Geometry3K 子集(几何题,答案可解析)或 ChartQA(图表数值,字符串可比对);
- 底座:Qwen2.5-VL-3B-Instruct,LoRA(rank 32 挂语言侧);
- 奖励:
答案正确=1(正则抽取后比对)+格式正确=0.2(<answer>标签)——先用最简奖励跑通; - 训练:TRL
GRPOTrainer,G=8,单 4090 起步(3B+LoRA 约 20GB 内);几百 step 后看两个曲线:奖励均值(在学习吗)与回答长度(R1 现象:往往先变长后收敛); - 评测:训练前 vs 后在留出集上对比 + 消融”去掉格式奖励/去掉视觉输入”(后者检验模型是否真在看图——防”语言先验作弊”是这个方向审稿必问)。
升级版选题(差分点):奖励设计的消融学(格式奖励会不会挤压思考?)、工具调用动作空间的取舍、“过程奖励 vs 结果奖励”在视觉任务上的对比、幻觉与 RL 的相互作用(RL 会不会强化自信的错误?)。
4. 审稿人视角的三个 open problem(你的论文切口)
- 奖励作弊(reward hacking):格式猜答案、先验蒙题——“去掉视觉输入性能不掉”是红灯;解法方向:对抗性验证集、过程监督;
- 推理链与视觉证据脱节:长 CoT 可能是”语言独角戏”,视觉 token 只进不出——评估”思考中是否真的利用了视觉”是新基准要害(涉及评测体系 3.7);
- 数据效率与冷启动:长 CoT 冷启动数据贵,GRPO 冷启动不稳定——蒸馏多少、RL 多少的最优配比未知。
5. 与你方向的接口
这套引擎完全可平移到美术学交叉带:美学评分的可验证化(人对齐偏好做奖励 → 8.2/8.6)、“先局部观察名画细节再回答”的看画 agent(thinking with images 的艺术版)、构图推理的过程奖励。领域+热门引擎 = 你的舒适发射位。
6. 自测题
- RLVR 在视觉领域”平移”的关键是什么?(找到天然可验证的奖励源——答案可解析/框可算 IoU/任务可判完成)
- 三条路线分别把什么当作”动作”?(思考 token / 视觉工具调用 / 过程步骤)
- 学生配方的两个最低成本消融是什么?(去格式奖励;去视觉输入)
- “去视觉输入性能不掉”说明什么?(语言先验在作弊,模型没看图——伪视觉推理)
- R1 现象指哪条曲线的什么行为?(回答长度随 RL 先增后稳——探索期学会铺开思考)
- 为什么 3B+LoRA 的 GRPO 是学生甜点?(组采样可小、LoRA 省显存、验证器零训练成本——2.10 的三因素在此聚齐)
7. 动手作业
- 跑通学生配方(哪怕只 500 step),repo 里放”训练前/后同题对比 + 回答长度曲线”两张图;
- 构造”作弊检测集”:从留出集挑 50 题,遮图重测,找出模型蒙对的题——写一页分析(这就是你理解 reward hacking 的第一手证据);
- 读 Vision-R1 或 DeepEyes 一篇,画出它的奖励函数与训练流程图,标注它对你配方的三处改进;
- 挑战:把任务换成”给定画作判断流派并给理由”,设计一个可验证奖励(流派标签可判分——思考:理由怎么验?)——把这个卡点写下来,它就是研究题。
图解与案例 · GRPO 的一次循环
flowchart TB
Q["问题 x(几何题/图表题)"] --> G["采样 G=4 个回答"]
G --> R["规则打分 r₁..r₄<br>(格式分 + 答案对错)"]
R --> A["优势 Aᵢ = (rᵢ − mean) / std"]
A --> U["好的回答抬概率 ↑<br>差的压概率 ↓(KL 系绳防漂移)"]
U --> NX["下一个问题 → 循环"]案例:四个回答的优势是怎么算出来的
奖励 (如格式分 + 答案对错的加权)。
mean = 0.5,std ≈ 0.354 → 优势 。
读出三件事:① 不需要价值网络——组内平均就是 baseline,同一题的四个回答互为参照,题目难度被自然消掉;② 推力按相对排名分配,而不是绝对分数;③ 若组内全对(std=0)→ 优势全 0 → 该题这轮白采。GRPO 对太简单和太难的题都天然无梯度——这既是省算力的特性,也是要靠课程数据(5.2)解决的效率问题。
8. 延伸资源
- DeepSeek-R1 论文——配方源头(2.7 已列,此处重读方法论节)
- EasyR1 / verl / TRL-GRPO 文档——三选一作为你的训练栈
- Visual-RFT / VLM-R1 类开源复现——代码级参考
附录 · 完整可运行脚本:grpo_math.py(RLVR 起点)
依赖:
trl>=0.14 peft transformers datasets(TRL 的 GRPO API 迭代较快——跑前对照你安装版本的官方文档核对参数名)。这是 5.1 §3 学生配方的文本版;多模态版只需把数据换成图文 prompt(Qwen2.5-VL 底座)。
# grpo_math.py —— Qwen2.5-1.5B + LoRA 在 GSM8K 子集上做 RLVR
import re, torch
from datasets import load_dataset
from peft import LoraConfig
from trl import GRPOConfig, GRPOTrainer
ANS = re.compile(r"<answer>(-?[\d,\.]+)</answer>")
def norm(s): return s.replace(",", "").rstrip("0").rstrip(".")
def reward_fn(completions, answer, **kwargs):
"""规则奖励:格式 0.1 + 答案正确 1.0(5.1 §3 的最简奖励)"""
out = []
for c, gold in zip(completions, answer):
m = ANS.search(c)
ok = m and abs(float(norm(m.group(1))) - float(norm(gold))) < 1e-4
out.append((1.0 if ok else 0.0) + (0.1 if m else 0.0))
return out
def to_prompt(ex):
gold = re.search(r"####\s*(.+)", ex["answer"]).group(1)
return {"prompt": [{"role": "user",
"content": ex["question"] + "\n请一步步推理,最后一行用 <answer>数字</answer> 作答。"}],
"answer": gold}
def main():
ds = load_dataset("openai/gsm8k", "main", split="train[:2000]").map(to_prompt)
cfg = GRPOConfig(
output_dir="out-grpo",
per_device_train_batch_size=8,
num_generations=8, # G=8:GRPO 的组大小
max_prompt_length=256, max_completion_length=320,
learning_rate=2e-5, bf16=True,
num_train_epochs=1, logging_steps=5, report_to="none")
peft = LoraConfig(r=32, lora_alpha=64, task_type="CAUSAL_LM",
target_modules=["q_proj","k_proj","v_proj","o_proj",
"gate_proj","up_proj","down_proj"])
trainer = GRPOTrainer(model="Qwen/Qwen2.5-1.5B-Instruct",
reward_funcs=[reward_fn], args=cfg,
train_dataset=ds, peft_config=peft)
trainer.train()
trainer.save_model("out-grpo/final")
if __name__ == "__main__":
main()
跑起来后盯两条曲线(5.1 §3):奖励均值(在学习吗)与回答长度(R1 现象)。然后做那两个最低成本消融:删格式奖励、遮题干数字。
5.2 数据为中心的 VLM 研究
本章目标:论证并教会”数据才是 VLM 的主战场”——架构已收敛(都是 LLaVA 变体),数据的差异才是模型差异。这是学生最友好的研究方向(算力友好、产业刚需、和你的 A1/D1 直接相连)。学完标准:能说出 VLM 数据的四大类、数据质量的五个可操作指标,并能设计一个固定模型只动数据的对照实验。
1. 为什么说”架构之争基本结束”
3.3 的 Q-Former 之死与 LLaVA-1.5 的胜利已经演示过一次:在数据和架构的对赌里,数据几乎总赢。2026 年的开源 VLM 公约数配置(3.5)进一步收敛了架构空间。于是研究价值向两端转移:一端是预训练范式(原生融合,巨头的事),另一端就是数据——SFT 混合配比、caption 质量、合成数据、去污染。产业侧同样如此:各家 VLM 的”秘方”公开的只有架构,真正保密的从来是数据管线。
2. VLM 数据的四大类(对照 3.2 的两阶段)
| 类别 | 服役阶段 | 质量要点 |
|---|---|---|
| Caption/对齐数据 | 阶段一 | 规模大、描述详实(“详注 caption”质量 > 短标签) |
| 指令/SFT 数据 | 阶段二 | 任务多样性(VQA/描述/推理/grounding 混合)+ 答案质量 |
| 偏好数据 | DPO/RM | 成对可比、标注一致性 |
| 可验证数据 | RLVR | 答案可自动判分(5.1 的奖励源) |
关键认知(LLaVA 的学术任务数据给过示范):指令数据可以从已有标注”合成”——用强模型把 caption/检测框改写成多轮对话和推理题。合成不是贬义词,是主流工艺;质量取决于改写模型和清洗标准。
3. 数据质量的五个可操作指标(研究/工程两用)
- 去重率:精确+MinHash 模糊去重后的重复占比(2.4 §1 的工具);
- 多样性覆盖:对 caption 做嵌入聚类,看簇覆盖与均衡度(一种画法/一种构图垄断 = 长尾塌缩);
- 信息密度:caption 的信息熵/长度分布——“一张图”三个字的 caption 是负资产;
- 图文一致性:CLIP 分数过滤 + 抽样人工核查(图文不对齐的样本毒害阶段一);
- 污染检查:与评测基准的重叠扫描(3.7 陷阱 1 的供给侧防治)。
4. 学生版研究配方:固定模型,只动数据
实验设计的干净版(控制变量法在 VLM 上的标准应用):
- 固定:底座(Qwen2.5-VL-2B)、两阶段训练配置、评测协议(冻结,3.7);
- 只动一个数据变量,测下游:候选变量——① caption 质量(短标签 vs 详注,可用强模型重写子集对比);② SFT 任务混合比(加 grounding 任务对推理的影响);③ 数据量 scaling(1k/5k/25k 曲线);④ 去重前后;⑤ 课程顺序(简单→难 vs 随机);
- 产出形态:一张”数据变量 → 多基准增量”的表——这就是一篇数据分析文的全部骨架,且免费卡或单张 4090 就够。
学术范式参照:Cambrian-1(2024)的”CV-benchmark 驱动的数据策展”——用评测表现反推数据配比,循环迭代;ShareGPT4V 类工作证明”只换更好的 caption,全基准普涨”。这两篇是本方向的必读样板。
5. 合成数据的风险清单(进组前必知)
- 模型近亲繁殖(model collapse):用模型生成数据训下一代,分布逐代收窄——多样化策略(多来源模型、混合真实数据)是主流对冲;
- 偏差烙印:合成器(GPT-4o 系)的风格/偏见印进学生模型(answer 长度、语气、甚至错误模式);
- 污染闭环:合成数据里混着评测题(合成器见过榜单)——供给侧也要做污染扫描;
- 标注者分歧的消失假象:合成数据”过于一致”,掩盖了任务本来的模糊性——评测时要留真实人工标注的锚点。
6. 与你的选题库接轨
8.9 里几乎每条线都吃这个方向的红利:A1 是”评测侧”的数据工程;D1(中国画数据集)是”领域侧”的数据工程;E2/E1 的 RL/DPO 需要”偏好/可验证”数据工艺。建议的复合路径:先按 §4 跑一个数据变量实验(练习+热身),再把方法论平移到你的领域数据(D1)上——同一个技能包用两次。
7. 自测题
- “架构之争结束”的证据两条?(Q-Former 之死;开源 VLM 公约数配置收敛)
- 四类数据各服务哪个阶段?(caption→对齐;SFT→行为;偏好→DPO/RM;可验证→RLVR)
- 五个数据质量指标里哪个最容易被忽视、后果是什么?(污染检查——训练评测重叠让一切实验作废)
- §4 配方为什么是”干净”的?(固定模型与协议、单变量动数据——控制变量法的标准应用)
- ShareGPT4V 类工作的核心发现一句话?(只把 caption 换成详注,全基准普涨——数据质量的红利直接可见)
- 模型近亲繁殖的机理与对冲?(合成数据训下一代→分布收窄;多源混合真实数据对冲)
8. 动手作业
- 下载 LLaVA 一份开源 SFT 数据子集,跑五个质量指标(写
data_audit.py),出”数据体检报告”; - §4 配方跑一个最小版:1k 短标签 vs 1k 详注 caption 的阶段一对比(免费卡可完成),看下游 caption 质量;
- 精读 Cambrian-1 的数据策展章节 + ShareGPT4V,各产出一页 6.1 模板笔记;
- 给 D1 写”标注规范 v0”(8.9 已布置)——用 §3 的指标定义验收标准。
9. 延伸资源
- Cambrian-1 论文(Vision-centric data curation)——本方向的方法论纲领
- ShareGPT4V 论文——caption 质量红利的最直接证明
- LIMA(2.5 已列)——“质量>数量”的文本侧先声
5.3 具身智能与 VLA:从"会说"到"会做"
本章目标:讲清 VLA(Vision-Language-Action)——把 VLM 的感知接到机器人动作的完整技术栈,以及学生在仿真环境里的下手处。学完标准:能画出 VLA 的通用架构,说清”动作怎么 token 化/怎么连续化”,能跑通一次仿真里的 VLA 微调。
1. VLA 是什么:VLM 的动作出口
VLA = 视觉-语言-动作模型:以 VLM 为骨干,输入图像+语言指令,输出机器人动作(机械臂关节角、末端位姿、移动底盘速度……)。它回答”多模态的终极形态”问题——理解世界是为了改变世界。本笔记各卷在此汇合:CLIP/DINO(1.5)当视觉塔、Qwen-VL 系(3.5)当骨干、token 化思想(3.4)管动作、RL(2.7/5.1)管后训练、世界模型(4.7)管仿真数据。
2. 关键设计:动作怎么输出(两大流派)
| 流派 | 做法 | 代表 | 取舍 |
|---|---|---|---|
| 离散动作 token | 动作离散成 bin,当词汇表外的”动作词”自回归输出 | RT-2、OpenVLA | 与 LLM 完全同构(一套栈);精度受 bin 分辨率限制 |
| 连续动作头 | VLM 输出特征,接 flow/diffusion “动作专家”生成连续轨迹 | pi0(flow matching)、RDT(扩散) | 精度高、适合灵巧操作;训练与推理更复杂 |
当前产业前沿(pi0 类)倾向连续头——flow matching(4.5 学的)直接用来生成动作序列,“生成模型”与”控制”在这里合流。指令跟随 + 多任务泛化是 VLM 骨干带来的核心红利:传统机器人策略一个任务一个模型,VLA 一个模型听人话干多任务。
3. 数据:具身的最大瓶颈
- 真机数据(遥操作演示)极贵——Open X-Embodiment(跨 20+ 机构、百万级轨迹)是”具身界的 ImageNet 时刻”尝试;
- 仿真数据(LIBERO、ManiSkill、Isaac Lab 等)便宜但存在 sim2real gap(仿真学到的到真机就水土不服);
- 生成式数据引擎是最新变量:4.7 的世界模型/视频生成给机器人造训练场景——巨头正在把”视频生成公司”和”机器人公司”合并叙事。
4. 学生路线:仿真里的 VLA(单卡可做)
最小可行项目:
- 环境:LIBERO 或 SimplerEnv(Python 包级安装,4090 跑得动);
- 底座:OpenVLA-7B 的 LoRA 微调(或更小的 SmolVLA/开源 mini VLA),任务集选 10 个仿真操作任务;
- 流程:下载 Open X-Embodiment 子集/LIBERO 演示数据 → LoRA 微调 → 仿真内评测成功率;
- 研究切口(单变量原则):视觉塔换 DINOv2 vs SigLIP 对成功率的影响;动作 bin 分辨率消融;语言指令改写(同义指令的鲁棒性——“把杯子放到盘子上” vs “把杯子挪过去”)。
与你的方向的接口:美术/文化领域的具身题(文物抓取的灵巧操作、修复协作机器人)是差异化叙事,但优先级低于先把仿真流程跑通——先 generic,再 domain。
5. 风险与机会的冷静评估
- 机会:产业增长叙事最陡(特斯拉/宇树/智元…),人才缺口真实存在;仿真研究单卡可做;与视频生成/世界模型的人才池重叠度高(你两头都学了);
- 风险:真机门槛客观存在(学生论文难落地真机 → 顶会评价偏仿真工作量);行业若进入整合期,纯仿真研究的边际价值会受挤压——对冲方式:把 VLA 当第二专长(你的主赛道仍是 VLM/多模态),简历叙事”多模态全栈 + 具身实践”。
6. 自测题
- VLA 与聊天 VLM 的架构差异一句话?(多了动作输出头——token 或连续轨迹)
- 两大动作流派各自的取舍?(离散同构 LLM 但精度受限;连续精度高但训练复杂)
- pi0 用什么生成动作?你在哪章学过?(flow matching 动作专家;4.5)
- sim2real gap 是什么?数据侧的三个对策?(仿真到真机的迁移鸿沟;真机数据/OXE 规模化/生成式数据引擎)
- 学生版单变量消融举两例?(视觉塔对比/动作 bin 分辨率/指令改写鲁棒性)
- “先 generic 再 domain”为什么是对的课程顺序?(通用流程没跑通前做领域化=在沙地上盖楼)
7. 动手作业
- 安装 LIBERO,跑通一个预训练策略的评测(不训练,先看到机器人在仿真里动起来——仪式感很重要);
- 用 OpenVLA 的开源 LoRA 脚本在 1 个任务上微调 500 步,对比成功率;
- 精读 pi0 或 OpenVLA 论文一篇(6.1 三遍法),产出配置卡;
- 挑战:设计”指令改写鲁棒性”评测集(每任务 5 种说法),测你的模型掉多少分——这就是一个基准型论文的种子。
8. 延伸资源
- RT-2 / OpenVLA / pi0 论文——离散派、开源派、连续派各一
- Open X-Embodiment 论文——数据版图
- LIBERO / SimplerEnv 文档——仿真起点
5.4 世界模型与空间智能:学会"预测世界怎么变"
本章目标:搞清”世界模型”这个词背后的四条技术脉络——视频预测、潜空间动力学、JEPA、3D 空间表征——以及它为什么同时被机器人、AGI、游戏三个行业押注。学完标准:能区分四种”世界模型”的形态,说清 JEPA 为什么主张”不在像素空间预测”。
1. 定义与思想源头
世界模型 = 对”状态-动作 → 下一状态”的内部模拟器:给定当前世界状态和动作,预测世界如何演化。思想源头是 Ha & Schmidhuber(2018)的《World Models》:小网络学会”在梦里训练”——先学一个环境模型,再在模型想象出的环境中练策略,不用真实交互。LeCun 的主张更激进:推理的本质就是在世界模型上做模拟规划——世界模型不是某个应用,而是 AGI 的地基。李飞飞的空间智能叙事则强调 3D:理解/生成可操控的三维世界。三条行业线(机器人、AGI 理论、游戏引擎)在此交汇。
2. 四条技术脉络(一张表分清)
| 形态 | 核心机制 | 代表 | 与本笔记的连接 |
|---|---|---|---|
| 视频预测型 | 生成模型直接预测未来帧 | Sora 类、Genie(可交互生成)、4.7 的合流 | 生成模型当模拟器 |
| 潜空间动力学 | 编码状态 → 学习潜空间里的状态转移 → 在想象中规划 | Dreamer 系(RSSM) | 强化学习的老朋友(2.7 的环境侧) |
| JEPA 家族 | 在表征空间预测(不重建像素),只预测”可预测的部分” | I-JEPA、V-JEPA(LeCun 系) | 自监督(1.5)的进阶哲学 |
| 3D 空间表征 | 显式三维(NeRF/3DGS/点云)作为空间记忆与生成目标 | World Labs 的 3D 场景生成 | 5.5 的 3D 章节预告 |
JEPA 的主张(本章最重要的思想):在像素空间预测未来会把模型容量浪费在”不可预测的细节”(每片树叶的抖动);正确做法是在抽象表征空间做预测——只学世界的可预测结构。这与扩散/自回归”重建一切”的哲学正面相对,是当前生成派 vs 表征派的核心分歧(业界有分歧,两派都有强证据,值得你各读一篇再站队)。
3. 为什么三个行业都在押注
- 机器人(5.3):真机数据太贵,世界模型 = 无限便宜的仿真环境(4.7 的生成式数据引擎是它的产品形态);
- AGI:LeCun 论证”LLM 缺世界模型所以不会真推理”——世界模型是自回归之外的第三条路;
- 游戏/影视:实时生成的可交互世界(Genie 类)重写内容生产管线——“生成式引擎”替代”渲染引擎”的长期叙事。
4. 评测:世界模型怎么打分
- 物理一致性(4.7 的 A 线思路):物体持久性、重力/碰撞合理、因果顺序;
- 动作条件性:给定不同动作,预测是否正确分化(区分”视频背诵”与”真正的动力学”);
- 反事实推理:“如果当时向左转会怎样”——模拟器的核心能力,也是最难的评测。
与 A1 的同构性:别人评测”画得像不像”,你评测”物理对不对”——领域化评测的红利逻辑完全一样。
5. 学生可做的三件事(单卡友好)
- 物理一致性基准(4.7 已列,本方向的正主):构造”违反物理”的探针集,测视频模型的世界知识;
- 玩具环境上的 Dreamer:MiniGrid/Atari 上复现 Dreamer(开源实现成熟,单卡一天级),画出”想象训练 vs 真实交互训练”的样本效率对比曲线——潜空间世界模型的教科书体验;
- V-JEPA 特征探针:冻结 V-JEPA 特征做下游(动作识别/物理属性判断),与 CLIP/DINO 特征对比——用 1.5/8.2 学过的探针方法论,回答”表征派学到了什么”。
6. 自测题
- 世界模型的一句话定义与思想源头?(状态+动作→下一状态的内部模拟器;Ha & Schmidhuber 的”梦里训练”)
- JEPA 为什么拒绝在像素空间预测?(容量浪费在不可预测细节;只学可预测的抽象结构)
- 四种形态各举一个代表与一章连接?(视频/Genie-4.7;Dreamer-RL;V-JEPA-1.5;World Labs-5.5)
- “动作条件性”评测防的是什么?(模型背诵视频而非学动力学——不给动作条件时多种未来应该分化)
- 三个行业各自的押注理由?(机器人省真机数据/AGI 推理地基/游戏内容管线)
- 生成派与表征派的分歧一句话?(重建一切像素 vs 只预测可预测的抽象结构)
7. 动手作业
- 在 MiniGrid 上跑 Dreamer 开源实现,记录采样效率曲线(环境步数 vs 回报)——亲身体验”梦里训练”;
- 冻结 V-JEPA 与 CLIP 特征,各训一个线性探针做”物理属性判断”(如碰撞后方向),对比准确率;
- 构造 20 条”物理探针”视频 prompt(球落地/水面倒影/织物摆动),测 2 个开源视频模型,写 300 字物理一致性观察——你的 A 线种子;
- 挑战:读 LeCun 的《A Path Towards Autonomous Machine Intelligence》§1,用三句话转述”自回归不是真推理”的论证,并写一条你的反驳。
8. 延伸资源
- Ha & Schmidhuber《World Models》(2018)——思想源头,博客版可读性极佳
- Dreamer V3 论文——潜空间动力学的集大成
- I-JEPA / V-JEPA 论文——表征派的宣言
- Genie 2(DeepMind)——可交互世界生成的现状
5.5 3D 视觉:NeRF → 3DGS → 前馈重建
本章目标:把 3D 这条”算力友好、科研活跃”的赛道讲成一条演化线——神经辐射场、高斯溅射、前馈大模型三代,以及它们与你的多模态主线的连接点。学完标准:能画出三代方法的核心表示,知道用自己照片跑一次 3DGS,能说出学生可做的四个方向。
1. 问题与表示的演化
任务:从一组 2D 照片恢复/重建/生成 3D 场景。三代方法的分歧全在场景用什么表示:
2. 第一代:NeRF(2020)——场景是一个函数
表示:MLP ——输入空间点坐标和视线方向,输出颜色和体密度;沿视线积分做体渲染,整条管线可微,用多视角照片的重建 loss 训练。
历史意义:3D 重建第一次变成”梯度下降训一个网络”——连续、可微、可接入一切深度学习管线。死穴:每个场景单独训几小时( MLP 里没存场景,训练过程本身在”记”场景)。
加速史:instant-NGP 用哈希网格把训练压到秒级——表示换成”可学习查找表+小 MLP”,思想延续(查表思路后来遍地开花)。
3. 第二代:3DGS(2023)——场景是一堆高斯
表示:场景 = 数十万个各向异性 3D 高斯(每个存位置、协方差、不透明度、球谐系数表示的视角相关颜色),用光栅化 splatting 渲染——不走神经网络前向,直接”喷”到屏幕上。
为什么赢:训练快百倍(分钟级)、渲染实时(>100fps)、表示显式可编辑(删一个高斯=删一个物体)、文件可嵌入网页。产业界(实景重建、影视预演、数字人)几乎一夜切换。与 NeRF 的关系:体渲染的思路保留,把”黑盒函数”换成了”显式图元”——又一次”简单显式打败优雅隐式”。
动手:nerfstudio/gsplat 框架 + 手机绕拍 30 张照片 + COLMAP 估计相机位姿 → 30 分钟得到可网页漫游的 3D 场景。这个作业的仪式感和收益都极高。
4. 第三代:前馈重建(2023–25)——3D 的”基础模型时刻”
NeRF/3DGS 都是每场景优化(拿照片现场训练)。前馈路线问:能不能像 ViT 一样,一次前向直接出 3D?
- DUSt3R(2024):两图输入 → 点图(point map)回归,免位姿重建;
- VGGT(2025,Meta): Transformer 一次前向吃几十张图,同时输出相机参数、深度、点图、3D 点轨迹——3D 领域的 SAM 时刻:从”每场景定制”到”通用即用”。
与本笔记主线的合流:VGGT 本质是”ViT 输出 3D 头”——卷1 的架构 + 5.4 的空间智能在此握手;视频生成模型(4.7)输出的若要有”可漫游的 3D”,也靠这条管线(视频→4D→3DGS)。
5. 生成侧一句话扫盲
文本/图像→3D:TRELLIS 类结构化 latent 生成、Splatter Image(前馈出高斯参数);视频→4D 动态场景。状态:几何质量可用、纹理仍靠贴图技巧——比 2D 生成落后一代,这正是空间(5.4 空间智能)要补的课。
6. 学生可做的四个方向
- 稀疏视角重建:只有 3–5 张图(最现实场景)的 3DGS/前馈改良——数据约束下的研究,算力友好;
- 3DGS 压缩与流式:几十万高斯 → 端侧可渲染(7.1 的显存思维平移);
- 文化遗产数字化(8.8 接口):文物照片 → 3DGS 漫游 + VLM 自动描述/知识挂接——与你导师方向交叉最强的 3D 题;
- 物理探针的 3D 版:重建场景的几何精度自动评测(A 线思路)。
7. 自测题
- NeRF 的输入输出和渲染方式?它”记”场景在哪?(坐标+方向→颜色密度;体渲染沿视线积分;场景存于 MLP 权重)
- 3DGS 换掉了什么、保留了什么?(隐式函数→显式高斯图元;体渲染思路保留、渲染换光栅化)
- 为什么产业一夜切换 3DGS?(快百倍+实时+显式可编辑+网页可嵌入)
- “每场景优化 vs 前馈”的分野?VGGT 为什么是”SAM 时刻”?(定制训练 vs 通用即用;一次前向出全套 3D)
- 3D 与你主线的两个握手点?(VGGT=ViT 输出 3D 头;视频生成→4D→可漫游 3D)
- 交叉最强的 3D 选题?(文物 3DGS 数字化 + VLM 描述——8.8)
8. 动手作业
- 完成 §3 的手机拍 + COLMAP + gsplat 全流程,产出网页漫游链接(作品集展示性极强的 3 分钟项目);
- 统计你场景的高斯数量与显存占用,试压缩(砍低不透明度高斯)看画质-大小曲线;
- 用 VGGT 开源权重对你手机照片做前馈重建,与 3DGS 结果并排对比(质量/速度/位姿精度三列);
- 挑战:读 VGGT 论文 §1–2,画它的 token 化与输出头结构——对照 1.4 的 ViT 图。
9. 延伸资源
- NeRF / 3DGS 两篇原始论文——各精读一遍(3DGS 的附录可视化极佳)
- instant-NGP / VGGT 论文——加速与前馈两站
- nerfstudio / gsplat 文档——工程直达
5.6 视觉 Agent 与 Computer Use:让模型操作你的电脑
本章目标:拆解”截图→理解→点击→完成任务”的多模态 Agent 全栈——grounding、动作空间、长时程误差累积、可验证奖励,以及安全边界。这是多模态落地最快的应用方向(企业自动化刚需)。学完标准:能搭一个最小 computer-use agent,并说清成功率瓶颈在哪一环。
1. 任务定义:GUI 是视觉 Agent 的完美舞台
人机界面天然是多模态的:屏幕是图像、任务用语言说、动作用坐标和键盘表达。为什么说它”完美”:① 环境标准化(所有人的电脑长差不多);② 任务可自动验证(文件删了没有/表单交了没有——5.1 的 RLVR 天然适用);③ 商业价值直接(办公自动化/RPA 的 AI 化)。Qwen2.5-VL 把 GUI agent 当头牌能力、Claude Computer Use、各大厂 Agent OS 战略,都在押这个场景。
2. 技术栈五层(画得出才算懂)
① 感知:截图 → VLM(分辨率要扛住 1080p+ 的小字——3.4/1.4 的 token 账在这最疼)
② 定位(grounding):"点击'导出'按钮" → (x, y) 坐标——可精确判分的核心子任务
③ 规划:任务分解("订机票"→查日期→选航班→填支付)+ 记忆(哪些步骤做过了)
④ 动作空间:click/type/scroll/hotkey/drag + 坐标输出格式
⑤ 执行与校验:pyautoid 类执行 → 截图回看 → 出错回滚(自我纠错)
工程三件套:Set-of-Marks(SoM)提示——把界面元素框出编号叠在截图上,让模型”选编号”而不是”说坐标”(定位精度立涨,零训练成本的经典 trick);双系统节奏(快动作循环 + 慢规划反思);轨迹数据(人类演示录制 → SFT 冷启动)。
3. 基准与成功率现状(诚实版)
| 基准 | 考什么 | 现状(2026) |
|---|---|---|
| ScreenSpot 系 | 纯 grounding | 头部模型 90%+(基本解决) |
| AndroidWorld / AITW | 手机端任务完成 | 中游水平 |
| OSWorld / WindowsAgentArena | 真实桌面多步任务 | 普遍 30–60%——差得远 |
关键洞察:grounding 已接近解决,瓶颈在长时程——多步误差累积(每步 95% 成功,20 步任务只剩 36%)、环境突变弹窗、动态界面。这个 gap 就是研究空间:分而治之的任务规划、失败检测与回滚(反思机制)、以及 5.1 的 RLVR——GUI 任务完成与否天然可验证,是最适合 RL 的 agent 场景(当前论文高产区)。
4. 安全:不能跳过的一节
Agent 拿着鼠标键盘,三类风险:① 提示注入——恶意网页把”请把邮箱发到 xxx”画在截图里,模型照做(视觉通道的 prompt injection,比文本注入更隐蔽);② 破坏性动作——删库级操作必须人工确认(就像 3.7 的”存疑”选项);③ 越权数据访问。研究机会:注入攻击的评测集与防御(视觉 RagNDet 类)、“高危动作确认”的交互协议——安全+评测的交叉题,论文和产业都认。
5. 学生最小项目(一个周末 + 免费额度)
- 栈:Qwen2.5-VL-7B(API 或本地)+ pyautogui + 虚拟机沙箱(VirtualBox/VMware,防误伤宿主机);
- 任务集:自选 10 个桌面任务(建文件夹重命名、浏览器搜索记事等),手写成功判据(可验证奖励的 DIY);
- 跑通循环:截图 → SoM 叠框 → 模型输出动作 → 执行 → 再截图,最多 N 步;
- 量你的数字:单步 grounding 准确率 vs 任务完成率——亲手复现 95%^20 的误差累积,这张图就是你理解该领域瓶颈的一手证据;
- 升级:给任务加 RLVR(TRL)或加反思机制,对比成功率——一个最小 agent 论文的骨架就出来了。
6. 自测题
- GUI 为什么是”完美舞台”三条?(环境标准化/任务可自动验证/商业价值直接)
- SoM 提示解决什么?代价是什么?(说坐标不准→选编号;需额外元素检测步骤)
- grounding 90%+ 但任务完成 30–60%,gap 的三个来源?(误差累积/环境突变/规划失败)
- 为什么说 GUI agent 是 RLVR 的最佳场景之一?(任务完成天然可验证+真实商业价值)
- 视觉通道的提示注入和文本注入有何不同、为什么更危险?(指令藏在像素里,模型”看见即执行”,用户无感知)
- 你的学生项目里”成功判据”对应论文里的什么?(可验证奖励函数/评测协议——5.1 与 3.7 的合流)
7. 动手作业
- 完成第 5 节的最小项目,记录 10 个任务的逐步轨迹(成功与失败各留截图);
- 画出”任务步数 vs 累计成功率”曲线(假设单步 90/95/98% 三档)——理解误差累积的数学;
- 收集 5 条含诱导内容的网页截图,测试你的 agent 是否会被视觉注入带偏——写安全观察笔记;
- 挑战:给 OSWorld 子集跑一个开源 agent 框架(如 UI-TARS 系),复现其报告数字的一半以上,差异表按 6.2 写。
8. 延伸资源
- CogAgent / UI-TARS / Qwen2.5-VL 技术报告的 agent 章节——grounding 与轨迹数据的一手做法
- OSWorld / AndroidWorld 论文——评测环境的设计思路
- 《Prompt Injection in multimodal agents》类论文——安全线
5.7 AI for Science 与医学影像:多模态的"硬价值"赛道
本章目标:把”AI for Science”从口号变成一张学生可切入的地图——以医学影像为主线(数据公开、任务清晰、与你学过的工具 90% 重合),旁及科学大问题的多模态接口。学完标准:知道医学影像任务的特殊性与公开数据入口,能启动一个合规的小项目。
1. 广义图景:AI for Science 的四个层次
- 结构预测:AlphaFold(蛋白质折叠,诺奖级)——“序列→结构”的生成/判别混合问题;
- 动力学模拟:GraphCast(气象)、分子动力学 surrogate——世界模型(5.4)的物理版;
- 发现与设计:材料筛选(GNoME)、药物分子生成(4.x 生成模型在分子 latent 上开分支);
- 科学感知:医学影像、显微/天文/遥感图像——本笔记的 CV/VLM 技能直接平移的主场。
共同母题:数据是稀缺、昂贵、带噪声的专家标注——“小数据 + 强先验 + 领域约束”的范式(与互联网大数据的 VLM 主线相反),这正是 CNN/混合架构(1.1 §6)与 U-Net(1.8 加星)仍是主力的原因。
2. 医学影像:你的技能 90% 平移的赛道
任务与数据(全部有公开入口)
- 分类/筛查:胸部 X 光(CheXpert、MIMIC-CXR)、皮肤镜(ISIC)——多标签分类 + 报告生成;
- 分割:器官/病灶分割(AMOS、BTCV; BraTS 脑瘤)——U-Net/nnU-Net 仍是学霸,MedSAM 是基础模型时代的新解;
- VQA/报告:VQA-RAD、SLAKE——医疗多模态对话(VLM 微调,卷3 全套技能);
- 3D:CT/MRI 体数据——1.9 的几何 + 5.5 的 3D 表示在此交汇。
三条特殊性(与自然图像的本质差异)
- 标签 = 专家知识:标注贵且标准专业(放射科报告是”弱标签”金矿——报告生成任务的天然监督);
- 分布偏移极端:不同设备/医院的域差(domain shift)比自然图像严重得多——泛化评测必须跨中心;
- 错误的代价不对称:漏诊远贵于误诊——评测要看敏感性/特异性 trade-off 而非单点准确率(8.2 的”分数的医学版”)。
合规红线(做之前必须懂)
患者隐私(HIPAA/个人信息保护法)、数据使用协议(公开数据集 ≠ 任意用途)、研究展示 vs 临床声明的边界——学生项目一律注明”研究用途,非临床决策依据”。
3. 学生启动配方(单卡,三个月)
- 下载 CheXpert 小子集 + nnU-Net 跑一个胸片分类基线(工具全现成);
- 用 BiomedCLIP(医学域 CLIP,1.6 的域内版)做 zero-shot 病症探针,对比训练基线——“域内基础模型价值”的一手数据;
- MedSAM 在你的分割任务上 vs 从零 U-Net——基础模型 vs 专属模型的老问题(1.7/8.4 同款对照);
- 升级(论文点):医疗 VLM 的幻觉评测(幻觉在医疗里是致命题——3.7/5.1 方法的严肃应用)。
4. 与你的主线的连接
- 方法侧:U-Net(1.8)、CLIP 探针(1.6/8.2)、VLM 微调与幻觉评测(卷3/5.1)、3D(1.9/5.5)——没有新知识,全是旧知识的域内组装;
- 方向侧:艺术与医学看似远,实则同构——都是”专家标注稀缺 + 主观性/专业性强的领域评测”(8.2 的美学评分 vs 医疗的敏感性评测是同一类研究形态)——你的方法论迁移成本极低;
- 就业侧:医疗 AI 是监管驱动的稳定赛道(不同于互联网的周期波动)——9.2 四条路里的避险选项。
5. 自测题
- AI for Science 四层次各举一例?(AlphaFold/GraphCast/GNoME/医学影像)
- 为什么医学影像里 CNN/U-Net 仍有主力地位?(小数据强先验——互联网大数据范式失效)
- 三条特殊性分别否定了自然图像的什么默认?(标注廉价/分布同质/错误对称)
- “报告是弱标签金矿”指什么?(放射科报告天然配图——报告生成任务的自监督原料)
- 医疗评测为什么看敏感性/特异性而非准确率?(错误代价不对称——类别极不平衡下准确率说谎)
- 学生项目的合规三件套?(隐私法/数据协议/非临床声明)
6. 动手作业
- 下载 CheXpert 小子集,跑通 nnU-Net 或简单 ResNet 多标签基线;
- 用 BiomedCLIP 做 zero-shot 病症探针(prompt 即病症名),与基线对比——写 200 字发现;
- 读 MedSAM 论文 §1,对比它和 SAM(1.7)的域适配策略;
- 挑战:设计”医疗 VLM 幻觉评测集”的方案页(10 个探针 + 判分协议)——5.1/3.7 的交叉练习。
7. 延伸资源
- nnU-Net 文档——医学分割的事实标准(跑通即懂一半)
- MedSAM / BiomedCLIP 论文——医学基础模型双代表
- CheXpert / MIMIC-CXR 数据卡——合规与结构说明(MIMIC 需认证课程,CheXpert 更易入手)
5.8 高效化:蒸馏、量化、剪枝与小模型
本章目标:把散落各章的效率技术(0.4 AMP、2.3 KV/GQA、2.8 量化、2.9 MoE/长上下文、3.3 token 压缩、3.5 ViR)收拢成一张”模型高效化”的全景图,并补上最后两块:蒸馏与剪枝。学完标准:能给”在 8GB 显存上跑一个能用的多模态模型”写出完整技术路线。
1. 全景图:高效化的五个杠杆
| 杠杆 | 原理 | 本笔记出处 |
|---|---|---|
| 降精度 | fp32→bf16→int8→4bit(数值表示压缩) | 0.2/0.4/2.8 |
| 蒸馏 | 大模型教小模型(能力迁移) | 本章新讲 |
| 剪枝/稀疏 | 删不重要的权重/结构 | 本章新讲 |
| 架构级 | MoE 稀疏激活、GQA、线性注意力 | 2.3/2.9 |
| 系统级 | KV 压缩、PagedAttention、token 压缩、分辨率路由 | 2.8/3.3/3.5 ViR |
组合定律:产业方案从不单用——FLUX-schnell(蒸馏步数 + 流匹配 + 架构)、InternVL3.5(ViR 路由 + Cascade RL + 部署优化)、Qwen 端侧(蒸馏 + 4bit)。“哪些杠杆能叠加、哪些互斥”是工程判断力的来源(量化与蒸馏可叠加;剪枝与量化同时上要小心误差叠加)。
2. 蒸馏:能力的搬家术
三阶段谱系:
- 经典 logit 蒸馏(0.3 的 softmax 家族):学生的输出分布对齐教师的(KL + 温度——温度让”暗知识”(次优选项的相对概率)显形,0.1 §3.4 的伏笔);
- 特征/关系蒸馏:对齐中间层特征或样本间关系(老 CV 的遗产,1.1 §4 表格里”知识蒸馏”的展开);
- LLM 时代两种形态:白盒(有权重:logit/特征对齐,如 MiniLLM)与黑盒(只有 API:让教师生成数据教学生——实质是数据蒸馏,2.5 的蒸馏 SFT、R1 的 distilled 系列、5.2 的合成数据都是这个家族)。
认知要点:现代”蒸馏”一词已扩到”用大模型造数据训小模型”——它与合成数据的边界模糊,核心都是能力从教师流向学生的通道设计。学生实验配方:固定你的领域任务,Qwen3-32B 造数据 → Qwen2.5-2B 学习,扫数据量画”蒸馏曲线”(多少教师数据能把学生顶到什么水平——5.2 §4 配方的蒸馏版)。
3. 剪枝:删冗余的艺术(概念级)
- 非结构化剪枝:删单个权重(稀疏度高但 GPU 吃不到加速——需要专用稀疏计算);
- 结构化剪枝:删整个通道/层/头(硬件友好,掉点风险大)——LLM 常用”层删除”(宽度不够深度来凑的反向操作);
- 现代简化:SliceGPT、短GPT 类”训练后剪枝”方案 vs 传统的”剪后重训”;与量化的关系:4bit 量化本身就是一种极限非结构化”压缩”(每个权重从 16bit 删到 4bit)——两者在”找到不重要的部分”上是同一个问题。
4. 端侧部署的现实(8GB 手机的账)
- 栈:llama.cpp/GGUF(2.8)→ Ollama(消费级体验)→ MLC-LLM/ExecuTorch(手机 NPU 编译);
- 账:8GB 手机扣系统剩 ~5GB → 3B 模型 4bit(1.5GB 权重 + 1GB KV + 系统)是甜点——端侧多模态 = 蒸馏到 2–3B + 4bit + 视觉 token 压缩(3.3)三件套;
- 端侧的特殊约束:首 token 延迟(模型加载)、内存带宽(手机 SoC 的 decode 速度)、功耗——评测维度与云端不同(7.4 的指标体系加”能耗”一列)。
5. 自测题
- 五个杠杆各举一个本笔记出处?(降精度-0.4/蒸馏-本章/剪枝-本章/MoE+GQA-2.3/2.9/系统-2.8+3.3)
- 温度在 logit 蒸馏里的作用?(放大暗知识——次优类相对概率)
- 白盒与黑盒蒸馏的区别?“数据蒸馏”属于哪类?(有权重对齐分布 vs 只有 API 造数据;黑盒——与合成数据同宗)
- 结构化 vs 非结构化剪枝的取舍?(硬件友好 vs 稀疏度高——GPU 时代结构化更实用)
- 8GB 手机跑多模态的三件套?(2–3B 蒸馏模型 + 4bit + 视觉 token 压缩)
- “哪些杠杆可叠加”举一对互斥风险?(剪枝+量化误差叠加;蒸馏与量化则可叠加)
6. 动手作业
- 蒸馏曲线实验:用强模型给你 8.5 的领域任务造 1k/5k/20k 条数据,训同一个 2B 学生,画”数据量→下游分”曲线——这份曲线同时是 5.2/5.8/8.5 三个方向的素材;
- 量化叠加实验:你的微调模型 fp16 → AWQ-4bit → 2bit(若可得),三档在留出集上的质量/显存/速度表;
- 端侧体验:Ollama 跑一个 3B 多模态模型,测首 token 延迟与功耗(拔电源看掉电)——端侧约束的实感;
- 挑战:读 R1 论文蒸馏节,回答”distilled 模型为什么不需要 RL 就有推理能力”——数据蒸馏的威力证据。
7. 延伸资源
- 《A Survey on Model Compression》类综述——全景对照(选读)
- R1 蒸馏节 / MiniLLM——两代蒸馏的代表
- llama.cpp / MLC-LLM 文档——端侧工程入口
6.1 如何读论文:三遍法与精读模板
本章目标:把”读论文”从耗时黑洞变成每天可执行的生产流程。学完标准:能用三遍法分诊任意一篇论文,并用统一模板产出精读笔记——这些笔记就是 8.9 选题和未来论文 related work 的原料库。
1. 三遍法(Keshav 经典框架的 ML 适配版)
第一遍·分诊(5–10 分钟):标题、摘要、图 1、结论。回答三个问题——类别(新方法/新基准/分析/综述)?主张(一句话)?与我有关吗(资源/方向/引用需求)?产出:精读/泛读/仅索引 三级分诊。纪律:90% 的论文应该停在第一遍——没有取舍的阅读等于没有阅读。
第二遍·通读(30–60 分钟):不看正文细节,先读全部图表(好论文的图表自成叙事);再读方法节框架和实验设置。回答:证据支撑主张了吗?每个实验在为哪句话服务?哪些设定可能藏猫腻(评测集重叠、baseline 弱)?产出:一页泛读笔记(模板见 §3)。
第三遍·精读(2–4 小时,只留给三类论文):①与你选题直接竞争;②你要复现;③领域必读经典。动作:假设你是审稿人——尝试在脑中”重构”方法:如果你来做,会怎么设计?再对照论文,差异处就是它的真实贡献(或问题所在)。推导逐行走,代码对着读。
技术报告(Qwen3-VL/InternVL 类)的读法不同:不逐节精读,按”配置清单”抽取——架构(3.1 四问)、数据配比、训练阶段表、评测结果四张卡,30 分钟归档。
2. ML 论文的”藏猫腻”清单(第二遍就该查)
- 评测集与训练数据隐性重叠(网络抓取数据的原罪,去重声明有没有);
- baseline 是否调到了最佳(还是只跑了默认参数当陪衬);
- 消融是否只删自己没用的组件;
- 增益的置信度(多 seed?方差?还是单次运行);
- “去除 X 性能不掉”类句子——反向消融往往比正向声明信息量大(5.1 的”遮图重测”就是它的视觉版);
- 大表里的小字:分辨率/步数/CFG/温度——生成类论文的结果强依赖推理设置。
3. 精读笔记模板(存成模板文件,每篇一份)
## 元信息
标题 / 会议年份 / 代码链接 / 一句话类别
## 问题与主张
它解决什么问题?(一句)
核心主张(claim)是什么?(一句,可证伪的形式)
## 方法一页
在 3.1 四问 / 生成模型三件套的框架里填空,画一张结构图
## 证据表
| 实验 | 支撑哪句主张 | 我的疑点 |
## 可复现性
数据/算力/代码开放度;我若复现:缩放到什么规模?(对照 6.2)
## 与我的课题
能借什么组件?竞争还是互补?引文追哪里?(← 未来 related work 直接抄这节)
## 一句话总结(写给别人听的版本)
4. 日常流程与工具(可持续 > 猛烈)
- 扫描(每天 15 分钟):arXiv cs.CV/cs.CL 新文标题摘要 + HF Daily Papers;用第一遍法分诊,只把 ≤10% 送进阅读队列;
- 队列纪律:队列超过 10 篇就是失控信号——砍掉旧的,收新的同理;
- Zotero:建”多模态/生成/美术学交叉/RL”四个分类,精读笔记 md 和论文 PDF 挂一起——你的笔记库会在写 related work 时以 10 倍效率回报你;
- 视频课(李沐精读)的定位:经典论文的”精读拐杖”——用它学怎么读,然后甩掉拐杖自己读新论文;
- 费曼出口:每篇精读写一段”三句话讲给实验室同学”——讲不出 = 没读通。
5. 自测题
- 三遍法各遍的产出物和停留比例?(分诊卡 / 一页泛读 / 完整精读;10% / 30% / 5–10%,其余仅索引)
- 为什么先读图表再读正文?(好论文图表自成叙事,是主张与证据的浓缩——也是猫腻最容易藏的地方)
- 哪三类论文值得第三遍?(竞争者/复现目标/领域经典)
- “反向消融”指什么?举一例?(删掉无关组件或输入(如视觉)看性能是否仍成立——检验主张的必要性)
- 技术报告和会议论文读法差在哪?(报告按配置清单抽取归档;会议论文走三遍法)
- 队列超过 10 篇说明什么?怎么处理?(阅读输入>消化能力;砍旧纳新)
6. 动手作业
- 把 §3 模板做成
paper-template.md存进笔记库; - 用三遍法处理本周 arXiv 的 5 篇新文(分诊比例如实记录);
- 选一篇做完整精读(建议 LLaVA-1.5 或 R1 类),产出笔记后向同学/录音讲 5 分钟;
- 建立 Zotero 库 + 四个分类,把本笔记引用过的论文全部入库。
7. 延伸资源
- Keshav《How to Read a Paper》——三遍法原文,15 分钟读完
- Zotero + Better BibTeX——工程配置十分钟
- 李沐《论文精读》——精读示范课
6.2 如何复现:最小复现方法论
本章目标:复现是学生科研的超能力——它同时训练工程、建立学术信誉、并常常直接长出研究题(8.9 的 B1 就是这么来的)。学完标准:能按”最小复现七步法”复现一篇论文,并知道复现失败时的三层归因。
1. 先立心法:复现的是什么
复现的对象是”可检验的主张”,不是”代码搬运”。把论文的核心 claim 写成一句话(例:“-1.5B VLM 在几何题上用 GRPO 训 500 步,准确率提升 ≥10%”),你的目标就是检验这句话——所有工程决策(模型多小、数据多少、训多久)都围绕”让这个检验在你的算力上成立”。
2. 最小复现七步法
- 提取主张:从 6.1 的笔记里抄出核心 claim 与关键数字(表 X 的 Y 行);
- 缩放设计:等比缩放实验(2.10 §2)——模型降档(7B→1.5B)、数据降档(100 万→5 千)、步数降档,但保持方法与对照的结构不变;写下”预期缩放后数字大约是多少”(趋势存在即可,不追绝对值);
- 找起点:官方代码 > 官方权重 > 第三方高星复现 > 从零写。读官方代码的实验配置文件先于读模型代码——真相在 config 里;
- 最小数据冒烟:1% 数据 + 最小模型跑通全流程(0.4 章单 batch 定律的多数据版);
- 对照实验:baseline(无方法)vs 方法配置,单变量切换——两条曲线的差才是论文主张的影子;
- 差异表:我的配置与论文逐项对比(数据版本/分辨率/步数/hardware/dtype),每差异一行——这张表是”没复现上”时的第一诊断依据,也是复现报告的核心产出;
- 归档:结论三选一——reproduce(趋势成立)/ partially(部分成立+差异表)/ refute(不成立+证据)。refute 也是有价值的产出(尤其复现的是热门论文时——但要谨慎和克制,先穷尽自己配置错误)。
Timebox 纪律:给整个复现设预算(如 2 周 / X 元卡费),到点交付”当前最好+差异表”——复现不是重写论文代码库,超过预算的”再修一个 bug”通常是沉没成本陷阱。
3. 复现失败的三层归因(按顺序自查)
- 我的 bug:数据管线、超参、评测协议(90% 在这层——尤其评测协议:指标实现差一行代码,结论全变);
- 论文的坑:未声明的关键细节(私有数据清洗、 cherry-pick 的 seed、隐藏的推理设置)——查官方 issue 区,常见”同问”;
- 领域级的坑:评测集污染、指标实现分歧、任务本身有上限——这层一旦确认,恭喜,你摸到了一个研究题(例:3.7 的评测陷阱、5.1 的 reward hacking,都是这么被发现的)。
4. AI 协作下的复现分工(vibe 时代的正确姿势)
- 让 agent 干:脚手架(数据 loader、训练循环样板、可视化)、文档检索(“这个 API 在 2.5 版本怎么用”)、代码逐行讲解;
- 必须自己干:主张提取(读论文)、缩放设计(算力账)、核心数学的验证(loss/梯度数值对拍,0.3 的习惯)、评测协议的逐行审查(复现翻车第一大源头)、结论判断;
- 红线:不要让 agent”照论文实现一遍”然后直接跑——它会把论文的笔误一起实现。先给它官方 repo 让它解释,再让它改你的配置。
5. 从复现到研究:三个升级开关
- 消融空白处:论文没测的变量(例:风格 LoRA 论文不测”复现度量化”——8.9/B1);
- 边界条件:论文只在某域成立(英文→中文?油画→工笔?小模型还行吗?);
- 主张放大:“他们消融里表现最怪的那一行”往往是新论文的引言第一段。 复现报告的”差异表+疑点清单”就是选题的孵化器——每次复现必须以一页”我能从这里往哪走”收尾。
6. 自测题
- 复现的对象是什么?工程决策围绕什么展开?(可检验主张;“让检验在我的算力上成立”)
- 七步法里哪步最容易被跳过、后果最重?(对照实验的基线配置——没有对照的复现等于没做)
- 差异表的两个用途?(失败诊断第一依据;复现报告核心产出)
- Timebox 的目的是对抗什么?(沉没成本——“再修一个 bug”的无限循环)
- 为什么评测协议要逐行自查?(指标实现差一行→结论全变;复现翻车第一大源头)
- 三层归因的顺序为什么是”我→论文→领域”?(先排除最常见、成本最低的解释;领域级坑一旦确认即研究机会)
7. 动手作业
- 选定一篇(建议 5.1 的某开源 RL 复现或 LLaVA-1.5),走完七步法,产出《复现报告》(含差异表与结论三选一)——这份报告直接进 repo 和作品集;
- 给报告写”我能往哪走”一页——与 8.9 选题库对照,看是否撞出火花;
- 故意练习一次 refute 归档(把某超参改成明显错的),体验”结论+证据”的写法。
8. 延伸资源
- 《Reproducibility in ML》类报告(ML Reproducibility Challenge 官网)——看看别人怎么写复现报告
- Papers With Code——官方/第三方实现检索起点
6.3 如何选题:价值判断、文献扫描与资源匹配
本章目标:把”找个好题目”从玄学变成流程。8.9 给了你 20 个现成题,这一章给的是出题的方法——毕业后你 forever 都需要它。学完标准:能独立完成一次文献扫描并产出一页纸 proposal。
1. 好选题的四条标准(缺一不可)
- 问题真实:有明确的痛点或空白(不是”没人做过所以做”——没人做可能因为不重要);
- 可检验:能设计出对照实验,且结论不会随评测协议的任意选择而翻转(3.7 的教训前置);
- 算力可负担:缩放设计后落在你的算力阶梯内(2.10 的三行公式先算再立项);
- 故事可讲:三句话能说清”什么问题-为什么难-我们怎么做”——讲不清的故事意味着问题定义还没完成。
新颖性 vs 有用性:初学者高估 novelty、低估 clarity+usefulness。一篇把评测做干净、把偏差量化清楚的分析文(A2 型),价值常高于一个含混的”新框架”。审稿人奖励的是”读者知道了一件事之前不知道”,不是”系统复杂”。
2. 文献扫描:从一篇到一张地图
- 种子:从综述/你已精读的论文出发(例:R1、LLaVA-1.5);
- backward 引用(它引了谁):找方法源头与领域骨架——顺着 related work 往回爬 2–3 层;
- forward 引用(谁引了它):Google Scholar 的 cited by——这个方向的最新动态和未解争端都在引用者里;
- 关键词矩阵:行=任务(美学/看画/grounding),列=方法(RL/DPO/数据/评测),格子=论文——空格子与薄格子就是候选题;
- 空白点三类信号:①主张无反向消融;②基准单一域(英文/油画)——平移即题;③两个热门方向还没握手(例:美学×RL=E2)。
产出物:一张一页的”文献地图”(矩阵+三类信号标注)——它同时是 proposal 的 related work 初稿。
3. 资源匹配矩阵(选题的最后一道闸)
| 维度 | 问自己 | 缺了怎么办 |
|---|---|---|
| 数据 | 谁的标注/采集人力?公开集够吗? | 换公开集多的域,或把”建数据”本身设为题(D1) |
| 算力 | 缩放设计后卡时×单价=? | 降模型档、缩短周期、选评测型题 |
| 合作者 | 导师的领域/艺术学院的接口? | 优先数据/评测类(对合作门槛低) |
| 兴趣 | 愿意为它熬三个周末吗? | 不愿意的题做不长——诚实 |
反模式清单:追热点裸奔(无资源优势地卷最卷赛道);大而全(“统一框架”式题目);纯增量调参(刷点无洞见);X+Y 缝合(两个词拼接但没有真问题);导师不认的题(资源闸门一票否决)。
4. 一页纸 proposal 模板(立项的标准格式)
## 题目(一句话)
## 问题与假设
问题:… ;假设 H:…(可证伪!)
## 方法概述
在 X 基线上加/改 Y,对照 Z(一张图)
## 实验矩阵
| 主实验 | 消融1 | 消融2 | 反向消融 |
(每个实验:数据/指标/预期结论)
## 算力与时间
模型/卡/卡时×单价;周计划(预留 1 周写论文)
## 风险与降级
若 H 不成立 → 最小可交付是什么?(评测集/分析报告兜底)
## 与现有工作的差异
相对 3 篇最近邻论文各差在哪(6.1 笔记的"与我的课题"节直接复用)
“风险与降级”是新手最该学的部分:任何实验都有 50% 概率假设不成立——立项时就写好兜底交付物(数据集、分析、负结果报告),你就永远不会空手。
5. 自测题
- 四条标准里新手最容易缺哪条?症状是什么?(可检验——评测协议含混、结论随协议翻转)
- 为什么 novelty 不是王?(审稿人奖励”读者知道了新东西”,清晰的分析文同样达标)
- 空格子三类信号各举一例?(无反向消融/单域基准/两方向未握手)
- forward 引用比 backward 多告诉你什么?(最新动态与未解争端)
- 反模式”X+Y 缝合”的病根是什么?(没有真问题——方法拼接替代了问题定义)
- 降级交付物的战略意义?(立项即兜底,假设不成立也不空手——科研的止损设计)
6. 动手作业
- 以 8.9 的 top1 题为种子,做一次完整文献扫描(backward 10 篇 + forward 10 篇 + 关键词矩阵);
- 产出文献地图一页 + 填完一页纸 proposal(找导师面谈的最终版本);
- 互相评审:把 proposal 给同学/贴给 AI,要求它找出”不可检验”与”缺对照”处——修到找不出。
案例 · 一个文献矩阵长什么样(迷你版)
案例:艺术×多模态的 3×4 矩阵
行=任务,列=方法,格子填你扫描到的论文(数量即该格的热度):
任务\方法 LoRA 微调 RAG 增强 RL/GRPO 评测基准 美学评分 ▓▓ 较热 ▓ 少 空格 ▓▓▓ 很热 看画理解 ▓ 少 ▓ 少 空格 ▓ 稀缺 grounding ▓▓▓ 很热 — ▓▓ 较热 ▓▓ 较热 两个空格(美学×RL、看画×RL)+ 一个稀缺行(看画评测)——对照 8.9 选题库:E2(小模型美学 RL)正好填第一个空格,A1 填稀缺行。矩阵的用法就一次:把直觉上的”没人做”变成格子里的”查无此格”。
7. 延伸资源
- 《How to do Research at MIT AI Lab》类经验文集——老但不过时
- ICLR/NeurIPS 审稿表(OpenReview 公开)——反向理解”什么题会被拒”
6.4 如何写作与投稿:从图表到 rebuttal
本章目标:让你第一篇论文少走一半弯路——ML 论文的解剖学、写作的正确顺序、投稿路径与时间线、rebuttal 的打法。学完标准:能独立搭出论文骨架并规划一条投稿路线。
1. ML 论文解剖学:每节在卖什么
| 章节 | 一句话职责 | 新手死法 |
|---|---|---|
| Abstract | 100 词讲清”问题-方法-结果数字” | 写成方法摘要,无数字 |
| Intro(1 页!) | 问题为什么重要+为什么难+我们的主张与贡献列表 | 文献综述化、贡献写成段落不写成列表 |
| Method | 把图 2 讲清楚——方法节的灵魂是那一张总览图 | 公式堆砌、与图脱节 |
| Experiments | 实验矩阵逐个回答”主张是否成立”(6.3 的实验矩阵直接展开) | 表格多但每表没指向哪句主张 |
| Related Work | 划清边界:“和我们最近的是 X,差异在 Y” | 流水账式罗列 |
| Limitation/Conclusion | 诚实交代边界——审稿人对诚实的作者更宽容 | 不写(必被审稿人补刀) |
贡献列表的写法:3 条以内,每条可验证(“我们提出 X,在 Y 基准上提升 Z%”),动词开头。
2. 写作顺序:图先行(反直觉但正确)
正确顺序:实验图表 → 表格 → Method(对着图写)→ Experiments 正文 → Intro → Abstract 最后。理由:图和表是你结果的物理存在,先固化它们,全文的叙事就定型了;反过来先写 intro 的人,通常会在实验做完后推倒重写。图 2(方法总览图)值得花一整天画好——审稿人对论文的第一印象 80% 来自它。
3. 工具链与格式
- Overleaf(协作标配)+ 目标会议官方模板(CVPR/NeurIPS/ACM MM 的 style 文件,页数硬限:正文 8 页、参考文献不计、supplementary 无限但审稿人没义务看);
- 图表:matplotlib 起步够用(统一字体字号、色盲友好配色、每图 self-contained 的 caption);不要用截图贴表格;
- 引文管理:Zotero + Better BibTeX 直接导 bib(6.1 的库直接复用);
- AI 协作的边界:语法润色、措辞建议、公式排版——可用;观点、实验叙述、贡献声明——必须是你的(各会议有 AIGC 使用披露政策,如实遵守)。中文写作→英文论文的三个要点:短句(一句一个意思)、主动语态、术语全篇一致(建一个术语表)。
4. 投稿路径与时间线(以 2027 视角)
路径:workshop(半年期,练手+拿反馈)→ arXiv 挂预印本(占优先权,进组后听导师的)→ 主会。主会时间线(截稿→开会约 4–6 个月):CVPR(11 月截)、ICCV/ECCV(交替年,3 月前后)、NeurIPS(5 月)、AAAI(8 月)、ACM MM(4 月,多媒体背景的你重点盯它)、WACV/ BMVC(更友好的 CV 次旗舰)。选会的策略听导师的——每个组有自己的目标档位与节奏。
Rebuttal( rebuttal 期 1–2 周)打法:逐条回应、先谢后答、能补实验就补(小实验的边际收益最大)、被误解的部分礼貌而坚定地澄清(“We apologize for the confusion. To clarify, …”)、绝不与审稿人争气。AC(领域主席)看的是 rebuttal 质量——它常是 borderline 论文的生死线。
5. 审稿人视角:最常见的五条拒稿理由(6.1 藏猫腻清单的镜子)
- 主张不清或不可证伪(没有明确的 claim);
- baseline 太弱或没调好(“和 strawman 打赢了”);
- 消融缺失(不知道增益来自哪个组件);
- 评测协议含混或可疑(3.7 的陷阱踩了一遍);
- overclaim(结论超出证据范围——limitation 不写的人常犯)。
自查法:投稿前把 6.1 的”藏猫腻清单”逐条问自己的论文——你挑别人刺的尺子,审稿人原样拿来挑你。
6. 自测题
- 为什么”图先行”?图 2 的特殊地位?(结果先固化叙事就定型;方法总览图是第一印象)
- 贡献列表的两条写法纪律?(≤3 条、每条可验证带数字、动词开头)
- workshop → arXiv → 主会路径各自的功能?(练手反馈/占优先权/正式成果)
- rebuttal 里”小实验的边际收益最大”是什么意思?(一个快速补的对照实验比千字辩护更能改变审稿人判断)
- overclaim 与 limitation 的关系?(不写 limitation 的论文几乎必然 overclaim——诚实是审稿人的宽容券)
- AI 写作协作的边界线?(润色可用;观点/叙事/贡献必须是你,且按会议政策披露)
7. 动手作业
- 把你的 8.9 top1 proposal 的实验矩阵,按 §1 的表格骨架扩写成一页”论文预骨架”(图表位置先留空);
- 找一篇你精读过的论文(6.1 的产出),反向画出它的”图表→主张”对应表——拆解一次别人的叙事结构;
- 挑战:写 200 字英文 abstract(用你 proposal 的数字),交给 AI 只做语言润色,对比修改点学写作习惯。
8. 延伸资源
- 《How to Write a Great Research Paper》(Simon Peyton Jones 的演讲)——一小时值得
- 《Writing for Computer Science》——选读
- OpenReview 上任意一篇你熟悉论文的 reviewer/rebuttal 全文——最好的一次性教材
6.5 开源贡献指南:用 PR 说话
本章目标:把”给开源项目做贡献”变成一条可执行的进阶阶梯——从改文档到核心功能。开源贡献是学生最被低估的履历资产:它同时证明工程能力、协作能力和社区声誉,且可以在面试里被验证(PR 链接挂在那,谁都看得到)。学完标准:在 30 天内完成你的第一个被合并的 PR。
1. 为什么值得(三个回报)
- 履历硬通货:
transformers/vLLM的 merged PR 在面试中的说服力超过任何课程项目——它经过了陌生工程师的严格 review; - 真实工程训练:读别人的大型代码库、写规范的 commit 和测试、处理 review 意见——这些是教程永远教不了的;
- 社区网络:review 你 PR 的人就是领域内的一线工程师——保研面试、实习内推的隐性人脉从这里来。
2. 贡献阶梯(逐级向上,每级都是真实的贡献)
| 级别 | 内容 | 难度/周期 |
|---|---|---|
| ① 文档/翻译 | 改错字、补示例、中文文档 | 半天/个——最佳第一步 |
| ② Issue 分诊 | 复现别人报的 bug、补充环境信息、确认/关闭 | 半天/个——练读代码 |
| ③ Bug 修复 | 带测试的小修复 | 1–3 天/个——含金量转折点 |
| ④ 新功能 | 先在 issue 里提案讨论,维护者点头再动手 | 1–2 周/个 |
| ⑤ 核心参与 | 长期 review 他人 PR、参与设计讨论 | 持续投入 |
选项目的原则:贡献你每天都在用的工具(LLaMA-Factory / transformers / peft / vLLM / lmms-eval——本笔记路线里的常客)。你踩过的每个 bug(7.2 案例集)都是 PR 机会:修好后顺手提 PR,“itch-driven”是最自然的贡献方式。
3. 标准流程与规范
fork → git clone 你的 fork → git checkout -b fix/xxx
→ 改动 + 补测试 → 本地过 CI(pytest/pre-commit)
→ push → 开 PR
PR 描述三段式(决定 review 速度):What(改了什么,一行)→ Why(关联 issue #号,复现路径)→ How tested(新增测试 + 手动验证步骤)。commit 规范:小步、动词开头(fix: guard against empty batch in collator)。Review 文化:意见来了 24 小时内回应;改不动就说明理由(礼貌而坚定——和 rebuttal 同款心法,6.4);被要求返工是常态,不是冒犯。
4. 找活干的三个入口
- 项目 issue 区的
good first issue/help wanted标签; - 维护者的 roadmap 讨论——提前认领即将要做的事;
- 你自己的 itch:文档里过时的 API、你复现论文时发现的 bug——最有把握的贡献来源。
5. AI 协作的边界
让 agent 干:写测试样例、补文档、查 CI 失败日志的原因、把你的修复翻译成项目的代码风格。必须自己干:理解 issue 的真实意图(很多 bug 报告本身是错的)、与维护者的讨论(社区信用是人护的)、对核心逻辑修改的判断(AI 不背这个责任,你的名字背)。红线:AI 批量生成的”水 PR”(改错字刷数量)会被维护者识别并拉黑——质量文化在开源社区是真实的淘汰机制。
6. 与作品集的联动(9.3 的加层)
- GitHub profile 上 pinned 一个”开源贡献”面板(merged PR 列表);
- 每个有分量的 PR 写一条知乎/博客(“我在 vLLM 里修了一个 KV cache 的 XX 问题”)——工程叙事的自然素材;
- 长期目标参考:一年 10 个 merged PR(3 个带测试的功能级)→ 足以支撑”具备生产级工程能力”的说法,且比任何证书都难造假。
7. 自测题
- 贡献阶梯的”含金量转折点”在哪一级?为什么?(③带测试的 bug 修复——证明能改真实代码且守规矩)
- 选项目的唯一正确原则?(贡献你每天在用的——有真实动机且你懂上下文)
- PR 描述三段式为什么能决定 review 速度?(What/Why/How tested 让维护者 30 秒建立信任)
- “itch-driven”是什么?它的优势?(修自己踩过的 bug 顺手提 PR;动机真实、上下文熟悉)
- AI 时代开源贡献的红线?(批量水 PR——社区的质量淘汰机制会拉黑你)
- 开源贡献对四条路(9.2)各有什么价值?(保研面试素材/复试工程证明/申请文书实例/校招简历硬通货)
8. 动手作业(30 天计划)
- 本周:给你最常用的工具(建议 LLaMA-Factory 或 lmms-eval)通读 issue 区,挑 1 个 good first issue 认领;
- 两周内:完成第一个 PR(文档级即可),走完 fork→test→PR→review 全流程——流程走通比改动大小重要;
- 把 7.2 案例集里你未来踩的 bug,凡是出在开源工具里的,修一个提一个(长期机制);
- 建
open-source-log.md:PR 链接/状态/review 教训三列台账。
9. 延伸资源
- 《First Contributions》repo——git 协作流程的 10 分钟演练
- 各项目 CONTRIBUTING.md——LLaMA-Factory/transformers 的都是优秀范本
- OpenSource.com 的 review 文化文章——社区软技能
6.6 学术诚信与 AIGC 时代的科研伦理
本章目标:在 LLM 无处不在的研究环境里,把”能做什么、必须披露什么、绝对不能做什么”的边界一次性画清。这一章 Protect 的是你未来五年最重要的资产——学术声誉。学完标准:能对任何灰色场景给出”行/披露后行/不行”的判断,并了解主要会议的现行政策要点。
1. 基础线(AIGC 之前就存在的铁律)
- 不剽窃:文字、想法、图表、代码都算——引了就是引了,包括”改写到看不出来”(这是最蠢也最常见的翻车);
- 不捏造:数据、实验结果、引用文献——幻觉引用是 LLM 时代的高发事故:AI 给你的参考文献必须逐条核实原文存在且内容相符;
- 不一稿多投/冗余发表:同一工作拆分发表、会议版与期刊版的重复率规范,各场所有细则——进组后按组规;
- 署名规范:署名 = 实质贡献(构思/执行/写作),“挂名”与”漏掉实际贡献者”都是违规;作者顺序按领域惯例(ML 界多按贡献协商)+ 导师决定。
2. LLM 使用的红绿灯(2026 主流政策的共识版)
| 用途 | 判定 | 说明 |
|---|---|---|
| 代码辅助(补全/调试/解释) | 🟢 普遍允许 | 前提:你能解释每一行并对其负责——审稿人问起不能答”AI 写的” |
| 语言润色/翻译 | 🟢 多数允许 | 部分会议要求在 acknowledgement 或政策表里披露 |
| 文献综述起草 | 🟡 谨慎 | AI 概括可以当线索,逐条核实原文后才可引用;禁止直接转述 |
| 把审稿内容/未发表稿件喂给 LLM | 🔴 禁止 | 保密性违规——多数会议明文禁止(等于把别人的未发表工作交给第三方) |
| 用 LLM 代写 review 意见 | 🔴 禁止 | 审稿是专业承诺,代写既不真实也违反责任 |
| 编造/篡改实验数据 | 🔴 永久红线 | 无论工具为何——撤稿+学术生涯终结级 |
实操守则:① 立一个”AI 使用记录”习惯(哪段用了什么工具——投稿政策表要填时 10 分钟搞定);② 引用只引你读过原文的文献(6.1 的 Zotero 流程天然防幻觉);③ 实验台账可追溯(2.10 的 csv)——被质疑时有完整证据链,这是你的”审计能力”。
3. 更宽的科研伦理(你的方向特有)
- 数据合规:爬取数据的版权与用途限制(8.7 的 datasheet 义务)、人像与隐私、文化敏感性素材的使用边界(8.1 §9 的在世艺术家问题);
- 模型滥用面:你的研究可能被反向滥用(鉴别 AI 图的研究 vs 深伪制作;风格迁移 vs 伪作制造)——发表时写清用途限定与风险讨论已是顶会惯例(broader impact);
- 利益冲突回避:审稿回避合作者/竞争者;引用自己人不能绕过独立评审;
- 对本笔记方法论的特别提示:本笔记由 AI 大量参与生成——你引用其中的说法去写作业/论文时,责任在你:关键论断回到原始论文核实(每一章的”延伸资源”就是为此设计的溯源路径)。
4. 灰色场景快判(自测即学习)
- 用 GPT 起草 related work 段落,逐条改成自己的话引用 → 🟡 只要不引用没读过的文献、且观点组织是你自己的——接近 🟢,但建议披露;
- 审稿期间把论文截图喂给 LLM 问”这方法哪有问题” → 🔴 保密违规,无争议;
- 实验跑出来不显著,只报告显著的那组 → 🔴 选择性报告 = 软性造假(诚实报告负结果反而受尊重,6.2 的 refute 文化);
- 在 appendix 用 LLM 生成图表 caption 并披露 → 🟢 允许(按会议政策表);
- 用 AI 把中文初稿译成英文投稿 → 🟢/🟡 润色级允许;“初稿思想都是 AI 的”则触及代写——思想必须是你自己的。
5. 自测题
- 幻觉引用为什么是 LLM 时代的高发事故?防线是什么?(AI 编造文献看起来完美;只引读过原文的——Zotero 流程防)
- “把审稿内容喂给 LLM”违反的是什么原则?(保密性——未发表工作交给第三方)
- 选择性报告显著结果为什么算软性造假?(破坏了实验矩阵的完整性——审稿人基于失真证据判断)
- 署名的定义与两个违规方向?(实质贡献;挂名/漏掉贡献者)
- 本笔记的特别提示是什么?(AI 生成内容的责任在使用者——关键论断回溯原始论文核实)
6. 动手作业
- 查 3 个目标会议(如 CVPR/ACM MM/NeurIPS)的 LLM 使用政策页,做一张对照卡(允许/披露/禁止三栏);
- 在你的实验台账模板里加”AI 使用记录”列;
- 挑战:写一篇 300 字的”个人科研诚信宣言”(你自己的红线清单)——进组第一天用得上。
7. 延伸资源
- ICLR/NeurIPS 官方 LLM 政策页——一手规范
- 《The Trustworthy Engineer》类学术职业指南——软技能面
- CRediT(贡献者角色分类)——署名的标准词汇表
7.1 显存估算速查与 OOM 排查大全
本章目标:把 OOM 从”玄学崩溃”变成”看一眼就知道谁在偷显存”。这是卷7 工程手册的开卷章——你未来两年报障最多的问题没有之一。学完标准:能给任意”模型×卡×配置”算出显存账,拿到 OOM 按决策树 10 分钟定位。
1. 训练显存总账(一张表吃遍天)
| 组件 | 每参数字节 | 条件 |
|---|---|---|
| 权重 | 2(bf16)/ 4(fp32)/ 0.5(4bit) | 由加载 dtype 决定 |
| 梯度 | 2(bf16)/ 4(fp32) | 只算 requires_grad 的参数(LoRA 只占增量部分!) |
| AdamW 状态 | 8(fp32 两个动量) | 同上,只算可训练参数 |
| fp32 主权重 | 4 | 混合精度训练才有 |
两种典型配置的算例(7B):
- 全参 bf16 混合精度:2+2+8+4 = 16 B/param → 112 GB + 激活 → 单卡无解;
- LoRA(rank 32,可训练 0.5%):权重 14 GB(冻结,只存不更新)+ 梯度/状态 ≈ 0.7 GB + 激活 → 24 GB 卡上还剩 ~8 GB 给激活。这就是全书的”LoRA 甜点”底层数学。
激活值的账(大头且常被忽略):约等于 seq_len × batch × hidden × layers × 常数(10~30) × bytes——随序列长度线性、随 batch 线性。视觉 token 多(高分辨率)或长文本时它先爆。gradient_checkpointing 用重算换存储,激活降到约 1/√层倍数级别,代价 ~30% 速度。
2. 推理显存账(2.3/2.8 的合并速查)
- 权重:同上表;
- KV cache =
2 × layers × d_kv × seq × batch × bytes(GQA 后 d_kv 缩小数倍); - 临时峰值:采样/解码时的 logits(vocab_size × batch,大词表模型不小)。
例:7B(L=32, d=4096, MHA, bf16)4k 上下文单条 KV ≈ 2.1 GB(2.3 已算)——并发服务里 KV 通常比权重先爆,所以 vLLM 把 gpu-memory-utilization 和 max-model-len 当第一杠杆。
3. OOM 排查决策树(按此顺序,10 分钟定位)
第 0 步:先测量,别猜。torch.cuda.max_memory_allocated()/1e9(训练循环里打印峰值)、nvidia-smi(谁在占卡)。多进程残留(上次崩掉的 python 僵尸、未释放的 vLLM)是”明明没跑啥却 OOM”的第一嫌疑——nvidia-smi 里找进程,kill 干净。
- 降 batch / 加梯度累积(激活线性降,等效更新不变)——成本最低,先动它;
- gradient checkpointing(激活换时间)——LoRA/微调场景标配;
- 查 dtype 混用:某个模块没被 autocast 包住、偷偷 fp32;4bit 底座配了 fp16 的 LoRA——统一 bf16;
- 查”忘记 no_grad 的循环”:训练中途的验证循环没包
inference_mode()→ 激活全存梯度 → 峰值翻倍(新手 OOM 榜第一); - 查”tensor 收集器”:日志列表里存了 loss tensor / logits(应立刻
.item()/ 只存标量); - 序列与分辨率:cutoff_len 降档、图片分辨率降档、视觉 token 压缩(3.3)——长尾样本(最长那条文本/最大那张图)引起的 OOM:先跑
max(len)统计; - 碎片化:峰值远小于总量却 OOM →
PYTORCH_CUDA_ALLOC_CONF=expandable_segments:True; - 最后手段:FSDP/DeepSpeed ZeRO(7.3 的主题——优化器状态分片,单机多卡或多机)。
4. 速查卡片(贴墙上)
| 卡 | 全参训 | LoRA 微调 | 4bit LoRA | 推理 |
|---|---|---|---|---|
| 24G(4090) | ≤2B | ≤7B | ≤13B(紧) | ≤13B bf16 |
| 48G(A6000/双4090) | ≤4B | ≤14B | ≤30B | ≤30B 4bit |
| 80G(A100) | ≤13B | ≤70B LoRA | 70B | 70B 4bit / 13B bf16 |
(量级参考,实际再留 20% 余量给激活与框架开销。)
5. 自测题
- 全参 bf16 混合精度每参数 16 字节怎么组成?(权重2+梯度2+AdamW 8+fp32主权重4)
- 为什么 LoRA 的梯度/优化器状态只占增量参数?(只有 requires_grad 的参数才有梯度和动量)
- 激活显存随什么线性增长?两个降它的手段?(seq×batch×hidden×layers;降 batch/降 seq、gradient checkpointing)
- “训练中途验证就 OOM”的机理?(验证循环没包 no_grad/inference_mode,激活带梯度图)
- 峰值远小于显存总量却 OOM,最可能是什么?(碎片化——expandable_segments;或多进程残留)
- 长尾样本 OOM 的预防?(先统计 seq len / 分辨率分布,cutoff 或分桶)
- 推理服务先爆的是权重还是 KV?(并发场景 KV 先爆——max-model-len×并发 的预算要算)
6. 动手作业
- 写
mem_report.py:打印权重/梯度/优化器分段显存 + 峰值(torch.cuda.memory_summary),在 2.6 的 LoRA 训练里挂上,对照 §1 的账验证误差 <10%; - 故意制造五种 OOM(忘 no_grad / 存 tensor 列表 / batch 拉满 / dtype 混用 / 僵尸进程),每种用 §3 决策树定位修复——你的第一次 OOM 演习;
- 给 8.9 选定题目的模型配置算一遍显存账,写进 proposal 的”算力与时间”栏。
图解 · OOM 排查决策树
flowchart TD
O["OOM!"] --> M0["第 0 步:先测量<br>max_memory_allocated + nvidia-smi"]
M0 --> Z{"僵尸进程 / 残留占用?"}
Z -->|是| K["kill 干净,重跑"]
Z -->|否| B["① 降 batch + 梯度累积"]
B --> GC["② 开 gradient checkpointing"]
GC --> D["③ 查 dtype 混用 / 忘 no_grad / tensor 收集器"]
D --> L["④ 降 seq len / 分辨率 / 压视觉 token"]
L --> FR{"峰值 ≈ 总量仍 OOM?"}
FR -->|是,碎片| FS["PYTORCH_CUDA_ALLOC_CONF<br>=expandable_segments:True"]
FR -->|否,真不够| FSD["FSDP / DeepSpeed ZeRO(7.3)"]使用方式:OOM 时从顶部往下走,每走一格只改一个变量并重测——“一次改三处再跑”会让你永远不知道是哪招起效的(这也是所有调试的元规则)。
7. 延伸资源
- PyTorch 官方《Understanding GPU Memory》博客——官方版账本
- HuggingFace《GPU inference》文档页——推理侧速查
- DeepSpeed / FSDP 文档——单卡装不下时的下一站(7.3 展开)
7.2 训练调试案例集:十大经典翻车与处置
本章定位:卷0/卷1/卷2 各章的失败模式在此汇成一本”案例字典”——先收录行业经典 10 例,后续用你的真实踩坑按同款模板追加(格式:现象/第一嫌疑/修复/预防)。学完标准:遇到异常能按”现象→嫌疑排序”30 分钟内定位,而不是改一行跑两小时地瞎试。
0. 通用排查流程(先背这个再翻案例)
症状分类 → ① 不收敛类(loss 不降/NaN/震荡)
→ ② 过拟合类(train↓ val↑)
→ ③ 评估异常类(训练正常但评测诡异)
→ ④ 资源类(OOM/速度骤降)
按类进案例 → 30 分钟无果 → 回到 0.4 单 batch 过拟合定律重新起手
案例 1:loss 第一步就 NaN
- 第一嫌疑:学习率过大;次嫌疑:fp16 溢出、脏数据(某样本 loss=inf)、loss 里对 0 取 log。
- 修复:lr 降 10 倍试;换 bf16;数据逐 batch 前向找出毒样本(二分法)。
- 预防:新 loss 写完先数值对拍(0.3 的习惯);AMP 一律 bf16。
案例 2:loss 卡在 ln(V) 不动
- 现象:语言模型 loss 恒等于 log(词表大小)——模型在”均匀猜”。
- 第一嫌疑:标签错位(忘 shift 一位、
ignore_index没设、pad token 参与了 loss)——教科书级 bug,人人踩过。 - 修复:手写一个 3 token 的小样本,纸上推 labels 对齐;检查
-100掩码覆盖。 - 预防:2.5 的 loss mask 单测;改数据管线必跑”3 样本人肉验证”。
案例 3:单 batch 过拟合降不到 0
- 诊断顺序(0.4 §7):标签对齐 → loss 实现(数值对拍)→ 数据预处理(归一化/resize 是否破坏)→ 梯度链(某层意外 detach/requires_grad=False;LoRA 时
print_trainable_parameters()是否为 0)→ 模型容量(太小)。 - 预防:0.4 四件套里的
debug_overfit.py常备。
案例 4:训练正常,验证精度诡异波动
- 第一嫌疑:评估循环忘切
model.eval()(dropout/BN 作祟);次嫌疑:评估预处理与训练不一致(resize 插值、归一化均值)、评估 batch 里的 pad 处理。 - 预防:训练与评估用同一个预处理函数对象;评估脚本单独过一遍单样本人肉检查。
案例 5:SFT 后模型复读机
- 现象:回答模板化、重复句式。
- 第一嫌疑:epoch 过多 × 数据过少(背下来了);次嫌疑:数据本身模板腔(蒸馏没清洗)、温度采样过低。
- 修复:减 epoch、数据多样性体检(5.2 的指标 2)、推理调 temperature/top-p。
- 预防:2.5 的失败模式三连实验(故意制造过)。
案例 6:微调后通用能力崩了(灾难性遗忘)
- 现象:领域任务变好,闲聊/常识变差。
- 修复:混入 1:1 通用数据、降 epoch、LoRA 降 rank、lr 降一档。
- 认知:这是 2.5 §5 的常态而非事故——评测必须含通用能力对照组。
案例 7:VLM 回答与图像无关(失明)
- 第一嫌疑:视觉特征没替换进正确位置(inputs_embeds 的占位 mask bug、
img_mask与占位 token 数不匹配);次嫌疑:projector 输出 dtype/scale 异常(对齐失败)。 - 修复:打印替换前后的 hidden states 逐位检查;阶段一 loss 曲线回看是否真的降过。
- 预防:3.2 复现时”训练前/阶段一/阶段二”三段对比图——失明在阶段一就会暴露。
案例 8:训练几小时后突然 OOM
- 第一嫌疑:训练中途的验证循环没包
inference_mode();次嫌疑:日志收集了 tensor、长尾样本(最长序列/最大图终于出现)、显存碎片累积。 - 修复:7.1 决策树第 0 步先看
max_memory_allocated与 nvidia-smi 进程。 - 预防:开工前统计 seq len / 图像分辨率分布,cutoff + 分桶。
案例 9:DDP 多卡训练 loss 行为异常
- 现象:多卡比单卡还慢/loss 抖动异常/每卡数据重复。
- 第一嫌疑:DataLoader 没用
DistributedSampler(每卡吃全量数据);次嫌疑:只在 rank0 做的操作(日志/保存)没包条件、梯度没同步(某些参数只在部分卡参与)。 - 预防:7.3 §3 的 DDP 检查单。
案例 10:训练时好好的,推理质量不对
- 第一嫌疑:chat template 错位(训练/推理不一致——2.5 头号 bug);次嫌疑:dtype 不一致(训练 bf16 推理 fp32 的量化误差、4bit 底座配置漂移)、权重没 merge 就加载了 base。
- 预防:训练脚本顺手导出推理配置(template/采样参数)随权重发布。
自测题
- 案例流程图的四类症状分别先查什么?(不收敛→lr/数据/精度;过拟合→数据量正则;评估异常→eval 模式与预处理一致;资源→7.1 决策树)
- 案例 2 为什么”人人踩过”?(next-token 的 shift 错位是最容易漏的 off-by-one——防线是 3 样本人肉验证)
- 案例群 5/6 共同的根因?(小数据 + 大改动 → 背诵或遗忘,都是”改动量与数据量不匹配”)
- 为什么案例 10 的 template bug 不报错?(它只是改变了文本分布——模型照样运行,只是输入格式陌生)
动手作业
- 建
debug-cases.md:把本章 10 例抄成检索卡(症状关键词索引); - 从 0.4/2.5/3.2 作业里故意复现 3 个案例,各写一篇”现场记录”(用了多久定位);
- 长期:以后每次翻车按模板追加一例——这本案例集一年后就是你最值钱的私产。
延伸资源
- Karpathy《A Recipe for Training Neural Networks》——流程层的总纲(0.4 已列,此处当字典用)
- PyTorch 官方 FAQ(显存/确定性)——底层疑难杂症
7.3 分布式训练入门:DDP、FSDP 与 DeepSpeed
本章目标:建立分布式的”概念地图 + 选择决策树”——你大概率不会手写通信代码(LLaMA-Factory/vLLM 全封装了),但必须知道每个选项在交换什么、出问题时日志在说什么。学完标准:能给任何”模型×卡数”组合选对并行方案,看懂训练日志里的 NCCL/ZeRO 字样。
1. 为什么分布式,两条轴
- 吞吐轴(数据并行):模型装得下,但想更快/更大 batch → 多卡各跑各的数据,梯度同步;
- 容量轴(模型并行/分片):单卡装不下 → 把模型本体切开分到各卡。 两条轴组合出 2.4 §5 提过的”3D 并行”(数据/张量/流水线)。学生 90% 的场景只涉及第一条轴 + 轻度分片。
2. DDP:数据并行的标准件
机制:每张卡一份完整模型,数据切开(DistributedSampler 保证不重叠);前向反向各自算,反向时梯度 all-reduce(全卡求平均)后同步更新——数学上等价于大 batch 单卡。
使用(LLaMA-Factory 或原生 torchrun 都是一行启动):
torchrun --nproc_per_node=2 train.py # 原生
# LLaMA-Factory: bf16: true, 即自动 DDP
检查单(案例 9 的预防):① DistributedSampler + set_epoch(否则每卡数据重复且打乱不变);② 只在 rank0 做日志/保存/评估(if rank == 0);③ BN 换 SyncBN(CV 模型);④ batch size 是每卡大小,总 batch = 每卡 × 卡数(调 lr 记得按总 batch 折算)。
3. FSDP:装不下时的标准解(ZeRO 思想的 PyTorch 原生实现)
问题:7B 全参训练要 112GB(7.1 的账)——单卡 24G 怎么办?分片:不存完整副本,把参数/梯度/优化器状态切到各卡,前向/反向用到哪片就临时 all-gather 哪片,用完即释放。
ZeRO 三级(理解级):ZeRO-1 切优化器状态(省 4×)→ ZeRO-2 加切梯度 → ZeRO-3(=FSDP full shard)连参数也切。代价:通信量涨(换显存),速度损失 20–40%。
实操(LLaMA-Factory 配置几行):
fsdp: full_shard auto_wrap
fsdp_config:
fsdp_offload_params: false # true=再卸载到 CPU(更省更慢)
4. DeepSpeed:另一个生态,多两件武器
微软系框架,ZeRO 概念的发源地,配置化程度高:
deepspeed: examples/deepspeed/ds_z2_config.json # stage 1/2/3
比 FSDP 多两件:ZeRO-Offload/Infinity(把优化器状态/参数卸载到 CPU 内存甚至 NVMe——显存极限换算力,学生租双卡机器跑 13B 的救命选项)和 流水线并行的成熟实现。FSDP vs DeepSpeed 怎么选:PyTorch 生态内/图省事 → FSDP;需要 offload 或多机流水线 → DeepSpeed。两者你都不用”会写”,只要”会配”。
5. 选择决策树(贴墙上)
模型 + 训练状态单卡装得下?
├─ 是,想提速/大batch → DDP
└─ 否 → 4bit/LoRA 能装下吗?(先降精度,总是第一选项)
├─ 是 → LoRA/QLoRA(不需要分布式!)
└─ 否 → 单机多卡? → FSDP(full_shard) 或 DeepSpeed ZeRO-2/3
显存还差口气? → + offload(CPU/NVMe)
多机大模型 → 3D 并行(Megatron/DeepSpeed,导师的事)
学生的真相:LoRA/QLoRA 甜点区(2.10)让你几乎不需要分布式——租多卡纯为加速时用 DDP,偶尔全参小模型用 FSDP。知道概念是为了看懂配置和日志,不是为了手写。
6. 通信常识(看懂日志的最低限度)
- NCCL:NVIDIA 的集合通信库,日志里的
NCCL INFO报错多半是网络/拓扑问题(单机几分钟后卡住不动 → 查 NCCL 超时与防火墙); - all-reduce:梯度求和再广播,数据并行的通信主角——通信时间 ≈ 模型大小 ÷ 卡间带宽,所以卡间带宽(NVLink vs PCIe)直接决定多卡加速比;
- 梯度累积 ↔ 通信:累积期间不需要通信(本地算完再同步)——慢网络下的省钱技巧。
7. 自测题
- 数据并行和模型并行分别解决什么轴?(吞吐/容量)
- DDP 数学上等价于什么?前提是什么?(大 batch 单卡;数据切分正确+梯度同步)
- ZeRO 三级各切什么?FSDP 对应哪级?(优化器状态/加梯度/加参数;full_shard=ZeRO-3)
- offload 交换的是什么?(显存 ↔ CPU/NVMe 带宽与速度)
- 学生”几乎不需要分布式”的原因?(LoRA/QLoRA 甜点让单卡装得下——2.10 的结论在工程侧兑现)
- 案例场景:双卡 DDP 训练两小时发现 loss 曲线和单卡一模一样但耗时没降——第一嫌疑?(DataLoader 没 DistributedSampler,每卡吃全量数据)
8. 动手作业
- 在 Kaggle 双 T4 上用 torchrun 跑你的 CIFAR 脚本(免费体验分布式),验证加速比(T4 走 PCIe,预期 ~1.8×);
- 读 LLaMA-Factory 的 deepspeed/f fsdp 配置示例,把每个字段映射到本章概念(写注释版配置);
- 挑战:用 FSDP(full_shard) 在双卡上全参训一个 1B 小模型——体验”装不下”到”装下了”的过程。
9. 延伸资源
- PyTorch FSDP 官方教程——概念与 API 双合格
- DeepSpeed 文档 ZeRO 页——配置字典
- 《Megatron-LM》论文选读——3D 并行的源头(知道即可)
7.4 推理部署与成本估算:把模型变成可运营的服务
本章目标:2.8 讲了”怎么部署”,这一章讲”怎么像工程师一样算账”——容量规划、单位成本、自建 vs API 的盈亏平衡,以及生产服务的工程细节。学完标准:能对一个真实需求出一份”部署方案+月成本”报价单。
1. 服务化架构(20 秒版)
客户端 → API 网关(鉴权/限流/计费统计) → 推理引擎(vLLM: 批处理/KV管理) → GPU
vLLM 起的 serve 已经把后两层打包成 OpenAI 兼容接口(2.8 实操过);你要补的是网关层的思维——限流(防止一个用户打满)、按 token 计量(usage 字段入账)、监控埋点。
2. 容量与性能账(7.1/2.8 公式的合并应用)
三步:① 显存预算 = 权重 + KV cache(并发数 × 上下文 × 单 token KV);② 吞吐上限 = 并发数 × 单请求 decode 速度(受显存带宽约束,7.1 的公式);③ 压测找拐点——并发涨到某处 TPOT(每 token 延迟)开始恶化,业务按可接受延迟取工作点。
一张 4090 跑 7B bf16 的量级感(实测经验值):单流 40–60 tok/s;并发 16 时总吞吐约 600–900 tok/s(TPOT 恶化到 ~0.3s)。
3. 单位成本账(本章核心,就业面试常考)
关键修正:利用率。上面的账假设 GPU 24 小时满载——真实服务有波峰波谷:
- 4090 自建(2 元/时)、满载吞吐 700 tok/s:2 ÷ 700×3600×10⁶ ≈ 0.8 元/M token;
- 利用率只有 10%(夜间没人用):实际 8 元/M token;
- 对照:主流 API(Qwen/GLM 级 7–9B)约 0.2–2 元/M token——API 集团比你便宜,除非你的利用率很高或需要私有化。
结论模板(给老板/导师的版本):“日请求量 < X 时用 API(弹性、免运维);超过 X 或有隐私/定制需求时自建,盈亏平衡点在利用率 Y%“。会算这个账,你在任何团队都值钱——大模型岗位的”降本”叙事全从这里来。
4. 部署形态选择
| 形态 | 适用 | 工具 |
|---|---|---|
| 单机自用/小团队 | 1–2 张卡,利用率低 | vLLM serve + Caddy/Nginx |
| 多租户多任务 | 一底座多 LoRA | vLLM --enable-lora 动态挂载(2.6 伏笔兑现) |
| 端侧/离线 | 隐私/无网 | llama.cpp + GGUF(Ollama 一键) |
| API 上游 | 不想运维 | 直接调 Qwen/GLM/DeepSeek API |
5. 生产工程细节清单(缺一样都是事故)
- 流式输出(SSE)——用户感知延迟的第一杠杆(TTFT 体验化);
- 超时与重试——生成没有”失败重试无害”的保证(重试要幂等设计);
- 限流:按用户/按 token 双维度(令牌桶即可);
- 监控四件套:吞吐、TTFT/TPOT 分位数(p50/p99)、显存水位、错误率——Prometheus + Grafana 是标配;
- 输入防护:max tokens 截断、special token 过滤(2.2 §4 的注入问题在服务侧防);
- 版本管理:模型版本与 API 版本一起打标——回滚能力比新功能重要。
6. 自测题
- 单位成本公式的最大误差源是什么?(利用率假设——满载 vs 实际波峰波谷差 10 倍)
- 什么条件自建才划算?(利用率高/隐私定制需求/有闲置卡——三占其一)
- 并发拐点压测测的是什么关系?(并发 ↑ → 总吞吐先升后 TPOT 恶化——工作点在延迟可接受处)
- 流式输出优化的是哪个指标的用户体验?(TTFT 的感知——先吐首 token)
- 多 LoRA 服务的价值?(一底座多任务动态挂载——几十 MB/任务 vs 14GB/任务)
- 给导师的部署建议为什么常是”先用 API”?(学生实验请求量低→利用率低→自建单位成本反而贵)
7. 动手作业
- 给你 2.8 部署的模型写一份”报价单”:假设日均 1 万次请求、每次 500 token 出 200 token 入,算 API 方案 vs 4090 自建方案的月成本(用真实 API 牌价与 2 元/时租价);
- 压测:并发 1/4/16/32 四档的吞吐与 TPOT 曲线(2.8 作业的完整版),标出你的工作点;
- 给 vLLM 前面挂一层 FastAPI 网关:限流 + usage 计量入库——一个周末的微项目,简历可写”完整服务化经验”;
- 挑战:Ollama 把 4bit 模型跑在本地 CPU/小显卡上,对比云端的延迟与质量——端侧路线的亲手账。
8. 延伸资源
- vLLM 生产实践文档(serving 配置与监控页)
- 《LLM inference cost calculator》类开源表格——行业牌价速查
- OpenAI 兼容协议文档——网关层的事实标准
7.5 数据 pipeline 工程:把数据当代码对待
本章目标:补齐”数据工程”这块最隐性但最值钱的工程能力——一条可复现、可回滚、可质检的数据管线。5.2 讲了”数据为中心的研究观”,8.7 讲了标注规范,这一章讲管线本身。学完标准:能为你的 A1/D1 数据搭出带版本管理的处理流水线。
1. 流水线全景(七个站,一个都不能少)
采集 → 清洗 → 去重 → 过滤 → 标注/合成 → 质检 → 版本化入库
第一原则:数据管线 = 代码。同样要版本控制、要测试、要可回滚——“数据是脏的”不是借口,“数据状态不可知”才是事故。
2. 清洗:脏数据的经典形态(图像侧)
- EXIF 旋转陷阱:手机照片的旋转信息存在元数据里——PIL 和 cv2 读取行为不同,训练/推理各自读出一度颠倒的图(经典静默 bug,3.2 的”分辨率不一致”近亲)。修法:入库时统一
ImageOps.exif_transpose并丢弃 EXIF; - 分辨率/长宽比规范化:按下游统一(VLM 场景记录原始尺寸);
- 色彩空间:CMYK/灰度混入 RGB 管线(统一转 RGB);
- 损坏文件:下载中断的截断图——
Image.verify()批检; - 内容过滤:模糊图(拉普拉斯方差)、低信息图(纯色)、水印/文字污染(OCR 检出即剔除——除非你在做文档数据)。
文本侧(caption/SFT 数据):语言识别(fastText)、长度分布截断、毒性/NSFW 分类器过滤、格式校验(JSON schema)。
3. 去重:两层工事
- 精确去重:图像感知哈希(pHash)/ 文本规范化后 hash——同一张图的字节变体;
- 模糊去重:图像用 pHash 汉明距离聚类,文本用 MinHash + LSH(2.4 §1 的工具落地)——近似重复(同一新闻的转载、同一风景的连拍);
- 最关键的一道:训练集与评测集的隔离去重(先定评测,再从训练侧剔除与评测近似的样本)——3.7 污染陷阱的供给侧防线。评测集加 canary(独有的蜜罐样本),管线跑完验证 canary 未泄漏。
4. 标注与合成的质检闭环
- 人工标注:8.7 的三把尺(kappa/锚点/模型预筛)——管线化即”每批次自动算 kappa、锚点混入、模型预标注排队”;
- 蒸馏标注(LLM 当标注员):先校准后使用——抽 200 条人工对齐,测一致率达标(如 ≥85%)才放行全量;连续监控漂移;
- 合成数据:生成 → 奖励/过滤器筛选(不合格不入库)→ 混合配比记录(5.2 的合成风险清单是这里的操作手册)。
5. 版本化:数据的 git
最小可行方案(不需要重型工具):
dataset_version: v1.3
source_manifest: urls.csv (hash: a3f...) # 原始来源清单+校验和
pipeline_commit: git-sha of preprocessing code
transforms: [exif_transpose, dedup_phash6, nsfw_filter@0.9]
stats: {count: 38214, dup_removed: 1207, ...} # 每版本必附统计
eval_split: eval_v2.lock # 评测集锁定文件(永不动)
每次管线变更 → 版本号 +1 → 旧版本保留(实验可比性)。进阶工具:DVC / wandb artifacts / HF datasets 的版本机制。论文投稿被问”用了哪个版本的数据”时,这页 yaml 就是答案。
6. 自测题
- EXIF 陷阱的机理与修法?(元数据旋转+不同库读取行为不同;入库统一 transpose 并剥离)
- 模糊去重的图像/文本各用什么?(pHash 汉明距离 / MinHash+LSH)
- “最关键的一道去重”是哪道?为什么?(train-eval 隔离去重——污染使一切实验作废)
- 蒸馏标注的放行条件?(抽样人工对齐达阈值才全量+持续监控漂移)
- 数据版本化要记录的最小五要素?(来源清单+哈希/管线代码版本/变换清单/统计/评测集锁)
- 为什么”数据状态不可知”比”数据脏”更严重?(脏可以洗,不可知则实验不可比、错误不可溯)
7. 动手作业
- 写
pipeline.py:对你 8.7/A1 的图像数据跑全流程(EXIF→损坏检→pHash 去重→分辨率统计),输出 §5 格式的 yaml; - 造 20 张”陷阱图”(EXIF 旋转/截断/近重复)喂进管线,验证每个过滤器都报警——给自己埋雷再排雷;
- 蒸馏标注校准实验:让 LLM 标 200 条流派标签,与你的金标准算一致率——得到”这条蒸馏管线可不可用”的数字;
- 挑战:给管线加 canary 验证步骤(评测集蜜罐检测)。
8. 延伸资源
- HuggingFace
datasets/datatrove文档——规模化工具 - 《Deduplicating Training Data Makes Language Models Better》——去重对模型的实证影响
- DVC 文档——数据版本化的重型方案(了解即可)
7.6 AI 协作守则:驾驭代码 agent 而不被其驾驭
本章目标:把 vibe coding 时代的正确姿势系统化——AI 是你的初级工程师,你是架构师+审查者。本笔记从 0.3 章(手写反向传播)就埋下的”亲手写核心”原则,在这里给出完整的操作体系。学完标准:有一套自己的 AI 协作工作流,且知道哪五类事绝对不外包。
1. 分工总表(本笔记的立身之约)
| AI 擅长(放心外包) | 你必须自己(绝对不外包) |
|---|---|
| 样板代码/脚手架/配置文件 | 核心数学:loss、梯度、attention(0.3/1.2 的作业逻辑) |
| 文档/README/注释 | 实验设计:对照/消融/协议(6.3) |
| 测试用例生成 | 结果判断:这个数字可不可信 |
| 报错解读/日志排查(7.2 的字典当它的教材) | 评测协议逐行审查(6.2 翻车第一大源) |
| 方案罗列与对比 | 责任:署名的是你(6.6 的红线) |
| 代码风格翻译/重构 | 品味:什么是好问题、什么是坏信号 |
2. 工作流五步(从”聊天”到”工程”)
- 拆任务:把需求拆成 AI 一次能做对的小块(“给 DataLoader 加 EXIF 处理”而非”帮我做数据管线”);
- 给足上下文:相关代码片段 + 报错全文 + 环境(版本)+ 约束(“只用 numpy,不要引入新依赖”)——AI 的输出质量与上下文质量成正比;
- 生成:先让它复述任务与方案再写码(对齐理解,省两轮返工);
- 审查:逐行读 diff——审查清单:shape 对不对、dtype 混没混、边界条件(空 batch/单样本)、是否幻觉 API(拿不准就去官方文档验证);
- 验证:单测 → 数值对拍(0.3 的习惯,AI 写的梯度尤其要拍)→ 单 batch 过拟合(0.4 第一定律)→ 小规模全流程。
3. AI 代码的四大典型暗坑
- 幻觉 API:自信地调用不存在的参数/方法——编译才炸,或更糟:静默走默认值。防线:关键调用查文档,CI 里开严格警告;
- 过度工程:三层抽象解决一个问题——可读性死亡。防线:要求”最简单可行版本”,重构时再允许抽象;
- 静默错误:语法全对、语义全错(广播错维、标签 shift 错一位——7.2 案例 2 的 AI 版)。防线:数值对拍+人肉 3 样本验证,不看跑得通,只看算得对;
- 上下文漂移:长对话后 AI 忘了早期约束。防线:项目约定写进
AGENTS.md/CLAUDE.md(数据格式/代码风格/禁区),长任务拆会话。
4. 学习保护条款(给学生最重要的三行)
- 核心模块第一遍必须亲手写——0.3 的引擎、1.2 的 attention、2.3 的 GPT,写完才有”手感”,此后才允许 AI 代劳同类的活;
- “能解释每一行”是署名的底线(6.6)——解释不了的不许进你的 repo;
- 定期”无 AI 日”:每周留一次全手写 session——手感是练出来的,不是读出来的。
5. 提问的艺术(上下文工程最小集)
一个好 prompt 的四要素:目标(要什么)+ 上下文(贴代码/报错/数据样例)+ 约束(版本/风格/不许做什么)+ 验收标准(“必须通过与 PyTorch 的对拍”)。反例:“帮我实现 LoRA”——它只能给你教程搬运;正例:贴出你的 nn.Linear 子类 + 报错 + “B 初始化为零、与 peft 实现对拍”。
6. 自测题
- 分工表里哪五类绝不外包?为什么核心数学第一?(数学/实验设计/结果判断/协议审查/责任——手感与署名都来自第一类)
- 工作流哪一步最常被跳过、代价最大?(审查——AI 代码”看起来对”,静默错误只能靠人肉审查+对拍抓)
- 四大暗坑的共同防线是什么?(验证纪律:对拍/单测/3 样本人肉——不看跑得通,看算得对)
- AGENTS.md 类文件解决什么问题?(跨会话的约定持久化——治上下文漂移)
- “无 AI 日”保护的是什么?(手感——初学阶段的肌肉记忆决定你能否审查 AI)
- 好 prompt 四要素缺一个会怎样?(缺上下文→幻觉;缺约束→过度工程;缺验收→静默错误)
7. 动手作业
- 给你的主力 repo 写一份
AGENTS.md(项目结构/数据格式/代码风格/禁区/验收标准); - 用 §2 五步流完成一个真实小任务(如 7.5 的 pipeline),全程记录”AI 输出 → 我抓出的问题”清单——第一次你就会震惊于静默错误的数量;
- 组织一次”无 AI 日”:手写 1.3 的 TinyGPT(不许查 AI,只许查 PyTorch 文档),与 AI 版 diff;
- 把你的 top10 提问模板存成 snippet 库。
8. 延伸资源
- 本笔记就是按本守则设计的教学品——每章”动手作业”都刻意放在 AI 的能力边界外
- Anthropic/OpenAI 的 prompting 官方指南——上下文工程的基础读物
- 《代码审查》类工程文化文章——审查清单的通用来源
8.1 美术学基础:给工程师的图像与美术学最小核心
本章定位:不是把你培养成艺术家,而是三件事——① 能和导师、艺术背景的协作者顺畅对话;② 为”计算美学 / 艺术生成 / 艺术理解”方向的研究打底;③ 将来你评测 AIGC 生成质量时,知道”好”到底好在哪,而不是只会说”看起来还行”。 本章不依赖任何前置卷,随时可读。建议读完就拿着第 10 节的问题清单去和导师聊一次。
1. 图像的三层框架(本章与全卷的骨架)
美术学看一张图,分三层。这个框架同时决定了”AI 能做到什么、做不到什么”,也就是研究机会所在:
| 层次 | 内容 | 例子 | AI 现状 |
|---|---|---|---|
| 形式层(Form) | 线条、形状、色彩、构图、光影、笔触、质感 | “高饱和互补色、三分法构图、硬光” | CV 最擅长,可计算、可量化 |
| 内容层(Content) | 题材、叙事、人物、符号 | “一位戴珍珠耳环的少女回眸” | VLM 已较好,细粒度仍易错 |
| 语境层(Context) | 时代、流派、艺术家意图、文化背景、艺术史位置 | “维米尔式荷兰黄金时代风俗画,暗箱技法争议” | 最难,是当前研究前沿 |
研究直觉:形式层已被自动化(美图软件、风格迁移),语境层几乎无法靠”看得更多”解决、需要知识与推理——所以你的科研机会在形式层→语境层的桥接:让模型不仅能描述画面,还能判断”这是谁的画风、哪一流派、构图如何服务于表达”。
2. 色彩
2.1 三属性与颜色空间
- 色相(Hue):是什么颜色(红/橙/黄…),色环上 0–360°。
- 明度(Value/Brightness):多亮多暗。
- 饱和度(Saturation/Chroma):多”纯”或多”灰”。
工程衔接:HSV/HSL 比 RGB 更贴近人的色彩直觉,所以图像 pipeline 里做色彩增强、数据增强(hue jitter)时常用它;直方图均衡、色彩校正都作用在这些分量上。另需知道 gamma 与 sRGB:人眼对暗部更敏感,所以图像文件用非线性 sRGB 存储,而卷积、上采样、扩散模型实际在”线性光”上数学性质更好——这就是为什么专业图像生成 pipeline 里常出现”先去 gamma 再处理”的操作,也是 diffusion 的 VAE 在 latent 空间工作但你调试时仍要懂色彩空间的原因。
2.2 色彩和谐与情绪(可计算!
美术学的色彩和谐有明确模式,全部可转化为算法:
| 和谐模式 | 定义 | 色环角度 |
|---|---|---|
| 单色 | 同一色相不同明度/饱和度 | — |
| 类似色 | 相邻色相 | 约 30° 内 |
| 互补色 | 对面色相(如红绿、蓝橙) | 180° |
| 分裂互补 | 互补色两侧 | 约 150°/210° |
| 三角色 | 等距三色 | 120° |
与研究的接口:把图像转 HSV 后对像素色相做统计,就能检测一幅画用了什么和谐模式;生成模型评测时,“色彩和谐度”可以变成一个自动指标,而不是纯主观打分。
色彩情绪的公认联想(用于 prompt 工程和评测):暖色(红橙黄)→ 温暖、紧迫、活力;冷色(蓝绿)→ 冷静、疏离、科技;高饱和 → 童话/海报感;低饱和 → 文艺/电影感;“莫兰迪色” = 高灰度的低饱和色系,近年 AIGC prompt 高频词。
3. 构图
3.1 常用法则(评测生成图时的 checklist)
- 三分法:主体放井字线交点,避免死板居中(但对称构图如建筑、肖像可故意居中求庄重)。
- 引导线:道路、河流、视线方向把眼睛引向主体。
- 框架构图:门窗树枝形成”画中画”。
- 负空间:主体周围留白,多则空灵、少则压抑。
- 视觉动线:观者扫图的顺序——优秀作品会”管理”这条路径;AIGC 常见失败是动线混乱(处处都是重点 = 没有重点)。
- 节奏与重复:元素的重复与渐变形成韵律。
3.2 与 CV 的接口(这是你和艺术同学合作时的共同语言)
- 显著性检测(saliency)≈ 计算化的”视觉焦点”;
- 视线追踪数据可以直接验证构图法则;
- Attention map × 构图:ViT 的 attention 可视化与”构图焦点”高度相关——“用 attention 分析生成图像的构图质量”是一个现成可做的交叉课题(见 8.9 选题库)。
4. 光影
- 三点布光:主光(定方向)+ 辅光(填阴影)+ 轮廓光(从背后勾边缘,把人物从背景里”剥”出来)。AIGC prompt 里的 rim lighting 即轮廓光。
- 明暗五调子:高光 → 亮部 → 明暗交界线 → 反光 → 投影。素描训练的核心;AIGC 的常见破绽是五调子不全(尤其反光和投影的物理不一致)——这也是鉴别 AI 图的线索之一。
- 硬光(点光源,边界锐利,戏剧感)vs 软光(面光源,过渡柔和,人像常用)。
- 术语对照:chiaroscuro(强明暗对比,卡拉瓦乔式)、Rembrandt lighting(伦勃朗光,单侧脸颊留三角亮斑)。
与研究接口:光影一致性是视频生成/世界模型的物理合理性核心指标之一;法线图(normal map)、深度图本质就是”光影的可计算替身”,卷5 的 3D 章节会再遇到。
5. 艺术史速览(为读文献和数据集服务)
西方主线(每段记:动机 + 视觉特征 + 代表人物):
| 时期/流派 | 视觉特征 | 代表 |
|---|---|---|
| 文艺复兴(15–16C) | 透视法确立、解剖精确、宗教/神话题材 | 达芬奇、米开朗基罗 |
| 巴洛克(17C) | 强明暗对比、动势、戏剧性 | 卡拉瓦乔、伦勃朗 |
| 印象派(19C后半) | 户外写生、破碎笔触、捕捉光色瞬间 | 莫奈、雷诺阿 |
| 后印象派 | 主观色彩与形变,通往现代主义 | 梵高、塞尚、高更 |
| 立体主义(20C初) | 几何解构、多视角并置 | 毕加索、布拉克 |
| 超现实主义 | 梦境逻辑、精细技法画荒诞 | 达利、马格利特 |
| 抽象表现主义(战後) | 行动绘画、色域 | 波洛克、罗斯科 |
| 波普/当代(60s–) | 大众图像、观念先行、媒介多样 | 安迪·沃霍尔 |
中国主线速记:工笔(精细勾勒设色,院体传统)vs 写意(笔墨简放重神韵,文人画传统);核心概念——笔墨(笔法+墨法的表现力,最难被 AI 捕捉的维度之一)、留白(负空间的东方哲学版)、诗书画印一体(一幅画是多模态作品——文本、图像、书法、印章的融合,天然的多模态研究对象)。数据集注意:WikiArt 里中国画样本偏少且标签粗糙,这既是坑也是机会。
6. 流派识别的”视觉特征向量”
给每个流派一个”如果只看形式层,看什么”的速查(训练流派分类器、做风格分析时直接用):
- 印象派:破碎短笔触、亮部不使用黑色、外光色彩(阴影偏蓝紫)
- 梵高/后印象派:厚重堆叠笔触(impasto)、高饱和互补色对撞、涡旋线条
- 立体主义:几何切面、同一物体的多视角拼合、低饱和土色系(早期)
- 超现实主义:精确写实技法 + 不可能的组合(精细质感 vs 荒诞内容)
- 波普:高饱和平涂色块、网点印刷感、复制与并置
- 中国写意:书法性线条、墨色浓淡干湿层次、大量留白、题跋印章
7. 术语中英对照(精简版,读论文/prompt 都会撞到)
composition(构图) · hue/saturation/value(色相/饱和度/明度) · palette(色调) · contrast(对比) · chiaroscuro(明暗法) · brushstroke(笔触) · impasto(厚涂) · impasto texture(肌理) · linear/atmospheric perspective(线性/空气透视) · negative space(负空间) · golden ratio(黄金比例) · still life(静物) · portrait/landscape/genre painting(肖像/风景/风俗画) · fresco(湿壁画) · oil/watercolor/ink wash(油画/水彩/水墨) · sketch(素描/速写) · underpainting(底层画) · glazing(罩染) · iconography(图像学) · provenance(流传有序/收藏史) · attribution(作者归属) · forgery(伪作)
8. 美术概念 → 可计算量映射表(本章最重要的表)
| 美术概念 | 可计算代理量 | 现成工具 |
|---|---|---|
| 色彩和谐 | HSV 色相直方图 + 色环聚类 | OpenCV/NumPy 即可 |
| 色调 | 色相均值/方差、饱和度均值 | 同上 |
| 明暗对比 | 亮度直方图的动态范围/分位数 | 同上 |
| 构图焦点 | 显著性图、规则三分带能量分布 | 现成 saliency 模型 |
| 笔触 | 局部梯度方向场统计、纹理特征(Gabor/LBP) | 传统 CV 即够 |
| 细节密度 | 频域高频能量、边缘密度 | FFT/Canny |
| 风格整体 | CLIP 图像嵌入的空间分布、“风格向量” | open_clip |
| 语境/流派 | VLM 零样本分类、微调分类器 | Qwen-VL 等 |
这张表的用法:任何”艺术 + AI”选题,第一步就是把美术学概念翻译成可计算量。翻译不出来的概念(如”气韵”)恰恰是研究空白。
9. AIGC 时代的美术学(为什么你的导师方向踩在风口上)
- 生成图像的美学质量评测正从主观打分转向可计算:美学评分模型(NIMA 起源)、人类偏好奖励模型(PickScore/ImageReward/HPSv2,卷8.6 详述)已成为文生图 RLHF 的核心组件——懂美术学的人 + 懂大模型的人,正是做这件事的稀缺组合。
- AI 图的”工业感”批评(平均化、缺乏笔触意图、五调子物理不一致)本质都是形式层问题,可检测、可对齐。
- 艺术风格 LoRA、线稿控制(ControlNet-lineart)让”风格”成为可微调资产,也带来作者权益、鉴定、水印等新问题——艺术史+法务+技术的交叉带。
10. 与导师对接:该问清楚的 10 个问题
- 您目前的具体子方向是哪一块?(美学评分/艺术生成/艺术理解/文化遗产/鉴定)
- 组里现有的数据集和算力是什么?自建数据还是公开数据集?
- 现在用的模型底座是什么?(VLM 微调?扩散模型?还是传统 CV)
- 组里在投什么档次的会议/期刊?(CVPR/ACM MM/数字人文期刊——决定了工作形态)
- 我进去先做什么:复现组里 baseline,还是从文献综述开始?
- 有没有艺术学院的 collaborators?合作模式是怎样的?
- 组里代码基础如何?有没有需要维护的训练框架?
- 近两年组里的毕业生去向?(读博/大厂 AIGC 团队——校准预期)
- 您觉得这个交叉方向未来三年最大的机会和风险是什么?
- 对我的技能路径,您建议先补 CV 还是先补生成模型?(对照本笔记路线图讨论)
11. 自测题
- 三层框架里哪层最难自动化?为什么这是机会?(语境层;需要艺术史知识与推理,恰是 VLM+RAG/知识增强的用武之地)
- 互补色和谐在色环上怎么定义?写出一个自动检测它的思路。(对顶 180°;色相直方图双峰,峰间距 ≈ 180°)
- 明暗五调子是哪五个?为什么可以用来鉴别 AI 图?(高光/亮部/交界线/反光/投影;生成图常物理不一致)
- “留白”对应西方的哪个概念?两者在数据集里各有什么表现?(negative space;中国画样本少而标签糙)
- 为什么说”笔墨”是 AI 最难捕捉的维度之一?(它是笔法+墨法的时序性、力度性表现,静态像素难以完全刻画——恰是笔触建模研究的对象)
- 给”莫兰迪色”一个可计算定义。(低饱和度带 + 有限色相范围的中等明度集合)
- 用第 8 节的表,把”这幅画很有呼吸感”翻译成两个可计算量。(负空间占比 + 显著性焦点数量/集中度)
12. 动手作业
- 挑 10 张名画(WikiArt 随机取样),手写”三层框架”分析卡:每张 3 行——形式/内容/语境。这是你未来给数据集做标注质量标准的雏形。
- 用 OpenCV 对其中 5 张算色相直方图,检验你肉眼判断的”主色调”是否被统计支持。
- 找 3 张近期 AI 生成图,用”明暗五调子”和”视觉动线”做体检,写下具体破绽——训练你的评测之眼。
13. 延伸资源
- 《艺术的故事》(贡布里希)——艺术史唯一必读,当故事读
- 《色彩与光线》(James Gurney)——写实绘画光影圣经,AIGC 圈公认的 prompt 素养书
- B 站搜”中央美院 公开课 美术史”+《中国美术史》相关纪录片——中国线补足
- WikiArt / Google Arts & Culture——高清图库与数据集源头
8.2 计算美学:让机器给"美"打分
本章目标:搞清”美学评分”这个研究方向的完整技术脉络——从数据集到模型到评测指标,以及它如何演变成今天文生图大模型的”美学奖励模型”。这一章是你和导师对话、以及未来选题的直接弹药库。前置:8.1(美术学基础)、0.2(PyTorch)。
1. 问题的形式化:主观的东西怎么变成学习任务
计算美学(Computational Aesthetics)核心任务:输入图像,输出”美学质量”分数。难点在于标注本质上是主观的,所以整个领域的方法论都在回答同一个问题:怎么处理人类评价的分布性。三种任务形式:
- 绝对评分:回归一张 1–10 的分。问题是不同人、不同图之间评分尺度不一致;
- 分布预测:预测所有标注者分数的分布(NIMA 路线,本章重点)——平均分抹平了”有人狂赞有人狂踩”的信息,分布才完整;
- 偏好排序:给两张图,只问”哪张好”(成对比较)——标注最可靠(人说不清 7 分和 8 分的差别,但”选一个”很容易),这是 AIGC 时代的主导形式(第 5 节)。
2. 数据集谱系(做研究先认数据)
| 数据集 | 规模/内容 | 标注形式 | 地位 |
|---|---|---|---|
| AVA | 25 万张摄影照片 | 每张约 200 个业余评审的 1–10 分 | 最大最常用,深刻影响方法设计 |
| AADB | 1 万张 + 属性 | 总分 + 构图/色彩等属性分 | 属性可解释性研究的常用数据 |
| SPAQ | 1.1 万手机摄影 | 总分 + 曝光/噪声等技术属性 | 技术质量 vs 美学分离 |
| WikiArt | 25 万件艺术品 | 流派/画家/题材标签(非美学分) | 艺术史任务(分类)的主数据源 |
| ArtBench | 6 万张 | 10 流派平衡分类 | 干净的艺术分类基准 |
| LAION-aesthetics | 数十亿图自动打分 | 模型分(不是人标) | 文生图预训练数据过滤的事实标准 |
注意趋势:人工标注数据集停留在几万到几十万张;而 AIGC 时代的数据过滤靠”模型自动打分”覆盖了亿级数据——你的研究可以卡在中间:领域专属(如中国画、书法、建筑摄影)的人工/半自动美学数据集几乎是空白。
3. 方法演化三阶段
阶段一:手工特征 + 传统模型(2008–2015)
色彩分布(8.1 章那张映射表的量)、构图规则符合度、清晰度、纹理复杂度 → 手工特征 → SVM 回归。今天读它的价值:这些特征依然是最好的可解释指标,且你的”美学先验”来自这里。
阶段二:CNN 分布预测(2015–2021)—— NIMA 是分水岭
Google 的 NIMA(Neural Image Assessment, 2018):用 ImageNet 预训练 CNN,输出端不是单个分数,而是 1–10 分的直方图(softmax),loss 用**Earth Mover’s Distance(推土机距离)**度量预测分布与标注分布的差异。
为什么这是正确的设计(必考理解):
- 评分本质是多峰分布(一大半人打 8,一小撮打 3),预测分布保留了”争议度”;
- EMD 考虑分数的有序性(预测 8 而真值 9,比预测 2 而真值 9 错得少)——普通交叉熵不知道 8 和 9 是相邻的;
- 部署时取分布均值当分数、标准差当”争议度”,一张图两种信息。
同期及后续:双列网络分别看”美学”和”技术质量”;把属性预测(构图/色彩/景深)作为辅助任务提升主任务。
阶段三:CLIP 化与偏好奖励模型(2021–至今)
两条并流的合流:
- 零样本美学:CLIP-IQA 等工作发现,在 CLIP 嵌入空间里构造”好照片 vs 坏照片”的文本探针(或直接分析嵌入方向),不用训练就能测美学——大模型的语义空间里”美”已经有位置。VLM 微调后做美学打分,效果持续刷新;
- 偏好奖励模型(preference reward model):文生图模型要”对齐人类审美”,需要奖励模型给生成的图打分来驱动 RLHF/DPO。代表:PickScore(百万级人类成对偏好数据训练)、ImageReward、HPSv2。它们的技术栈 = CLIP/VLM 底座 + 成对偏好数据 + Bradley-Terry 式排序损失(2.7 章 DPO 的同源思想)。
这条演化线的本质:美学评分从”独立任务”变成了”生成模型对齐的组件”——也就是说,它从一个冷门方向变成了文生图产业链的定价权环节:谁的审美标准好,谁生成的图就”好看”。这就是你导师方向的机会所在。
4. 评测指标(论文里怎么证明自己好)
- SRCC(Spearman 秩相关):不比分数绝对值,只比排序是否一致。为什么用它:标注噪声大,绝对分不可信,但”我认为 A 比 B 好”相对可靠。报告美学论文结果 90% 用它;
- EMD:分布预测任务(NIMA 式)用;
- 二分类准确率:高质量/低质量划分的任务用。
自己复现时的自查问题:测试集和训练集有没有按摄影师/主题划分?没有的话模型可能背下了拍摄者风格而不是学会审美——这是这个领域最经典的评测陷阱。
5. 可做的课题方向(结合你的背景与算力)
- 中文审美/画种美学数据集与基准:工笔/写意/书法/园林摄影——AVA 全是西式摄影,空白明显;半自动标注(大 VLM 打分 + 人工校验子集)控制成本;
- 可解释美学归因:用 8.1 章的映射表 + Grad-CAM/attention,让模型说出”扣分在构图”而不只是给一个分——评测透明化是真需求;
- AIGC 图美学评测:生成图”技术好但艺术差”(平均脸、过度平滑、构图平庸)——构建区分技术质量与艺术质量的评测协议,直接服务于生成模型后训练;
- 美学奖励模型的小模型极限:2B VLM + LoRA 能把 PickScore 式偏好建模压到什么程度——学生算力友好,且产业真需要端侧/批量打分的小模型。
选题前先做的事:问导师组里已有的数据/标注资源和在投的方向,课题从资源上长出来,不从论文空想。
6. 自测题
- 为什么 NIMA 预测分布而不是均值?(保留多峰争议信息;EMD 利用分数有序性)
- EMD 相比交叉熵在评分任务上好在哪?(知道 8 与 9 相邻、2 与 9 遥远——序数结构)
- 为什么美学评测主流用 SRCC 而不是 MSE?(标注噪声大,排序比绝对值可靠)
- AVA 数据集的标注结构对方法设计的影响?(每张约 200 人打分 → 天然的分布标签,直接催生 NIMA 设计)
- 成对偏好为什么比绝对打分可靠?它驱动了哪类现代技术?(人擅长比较不擅长标定;RLHF/DPO 的奖励模型)
- 按摄影师划分 train/test 是防什么?(背风格不学审美,数据泄漏)
- LAION-aesthetics 用模型分过滤亿级数据,这个链条的前提是什么?(有一个可信的美学评分模型——它自己又是从人标数据蒸馏来的;基础数据质量决定上层天花板)
7. 动手作业
- 下载预训练 NIMA 权重(或复现简化版:ResNet18 + 10 类 softmax 输出 + EMD loss),在 AVA 测试子集上算 SRCC;
- 自己给其中 50 张图打分,算”你 vs 模型”的 SRCC,再看不一致的图——用美术学语言写下你为什么不同意(这就是可解释性的研究素材);
- 用 open_clip 构造零样本探针(“a beautiful photo” vs “a bad photo” 嵌入差方向),给同一批图打分,对比 NIMA——体会”语义空间里美学已有位置”这句话的含义;
- 挑 20 张 AI 生成图过一遍模型分,记录”高分但你觉得平庸”的案例——8.6 章(AIGC 评价体系)的引子。
8. 延伸资源
- NIMA: Neural Image Assessment (Talebi & Milanfar, 2018)——必精读
- CLIP-IQA(Wang et al., AAAI 2023)——零样本美学开山
- PickScore / ImageReward / HPSv2 论文——偏好奖励模型三连
- AVA 数据集论文(Murray et al., 2012)——了解标注协议
8.3 风格迁移演化史:Gatys → AdaIN → 扩散时代
本章目标:用”风格的可计算定义”这根线,串起 2015→2026 的三代技术——并看清每一代到底捕捉了”风格”的哪一层(8.1 三层框架的照妖镜)。学完标准:能给三代方法定位与互相批判,能跑通任一时代的代表方法。
1. 先问:什么是”风格”的可计算定义
8.1 的三层框架在此处变成裁判尺:形式层(笔触/肌理/色彩分布)、内容层(画了什么)、语境层(谁画的/哪个流派/为什么这样画)。三代风格迁移技术的分歧,本质是”把风格简化成了形式层的哪个子集”。
2. 第一代:优化时代(Gatys et al., 2015)——风格 = 特征相关性
核心思想:用预训练 VGG 的特征表示两样东西——内容(深层特征图本身)与风格(Gram 矩阵:特征通道两两之间的相关统计 )。合成图 = 最小化”内容特征相似 + 风格 Gram 相似”:
洞察历史级:风格第一次被定义为”特征统计的相关结构”而非像素——它捕捉的恰好是笔触/肌理这类形式层属性。缺陷:对每张图做数百步迭代优化(分钟级);Gram 只见纹理不见构图与语义;“风格”被窄化为”笔触滤镜”(梵高的涡旋会出现在任何内容上,但梵高式的造型夸张与构图选择完全丢失)。美术学批注:它捕捉了形式层的肌理子集,内容层被强行保护、语境层为零。
3. 第二代:前馈时代(2016–2020)——风格 = 统计矩
- Per-image net → 通用前馈(Johnson 2016):训练一个网络”一次前向完成 Gatys 的优化”——快三个量级,代价是每个风格一个模型;
- AdaIN(2017,分水岭):把内容特征在每个通道上做均值方差归一化,再用风格特征的均值方差重新调制——风格 = 特征统计矩,一次前向任意风格;
- 后续变体(WCT、风格注意力、风格-内容解耦)都在更精细地统计化”风格”。
美术学批注:统计矩比 Gram 更全(色彩分布+对比度性格),但依然只在形式层打转;且实测中”风格迁移”常退化为”色调迁移+纹理贴附”——构图、笔势、造型语言这些更高级的风格属性始终缺席。这个”缺席”就是留给你的题(A4/B 线)。
4. 第三代:生成模型时代(2022–)——风格 = 可微调的分布
扩散模型把”风格”从”变换规则”变成了”生成分布的属性”,四条武器(4.6 已实操):
- 文本 prompt:最弱——词汇级的风格暗示(“in the style of X”),细粒度画种常常失灵;
- 风格 LoRA:最强——几十张图把分布微调过去,笔触+色彩+造型全谱系复现(4.6 的量化验收);
- IP-Adapter / 反演系(InST 类):单参考图注入风格,免训练但保真度低一档;
- 组合控制:ControlNet 管构图(内容层)、LoRA 管风格(形式层)、prompt 管题材——第一次实现三层分离控制,这是前三代做不到的。
美术学批注:LoRA 时代第一次让”造型语言/构图偏好”(不只是纹理)进入风格的可迁移集合——因为模型学的是分布而不是变换。新问题也随之诞生:风格复现度的量化评价(→8.7)、在世艺术家权利(8.1 §9)、以及”AI 复现的风格里丢失了什么”(意图与语境层依然为零——语境层需要知识与推理,是 VLM 的题,不是生成模型的题)。
5. 三代对照表(背下来)
| Gatys | AdaIN 系 | 扩散/LoRA | |
|---|---|---|---|
| 风格的可计算定义 | Gram 相关 | 统计矩 | 生成分布 |
| 捕捉到的层 | 肌理 | 肌理+色调 | 肌理+色调+造型/构图 |
| 代价 | 分钟级优化 | 快但浅 | 需训练/大模型 |
| 语境层 | 0 | 0 | 0(仍是零!) |
6. 自测题
- Gram 矩阵捕捉什么、丢失什么?(通道相关=纹理统计;空间布局与语义全丢)
- AdaIN 的”调制”在做什么?为什么比 Gram 快还全?(用风格特征的均值方差重调内容特征;一次前向+统计矩更全面)
- 为什么说扩散时代”第一次实现三层分离控制”?(ControlNet=内容层、LoRA=形式层、prompt=题材——正交可叠加)
- 三代共同的零是什么?为什么?(语境层——它不是像素分布的属性,是知识与意图的属性)
- Gatys 的历史地位为什么不可替代?(“风格=特征统计”的定义性洞察,后面所有代际都在它的概念地基上换实现)
7. 动手作业
- 用
torch.hub或 diffusers 跑一次 AdaIN(任意实现),与一次风格 LoRA 输出并排,用 8.1 三层语言写对比笔记(各捕捉到哪层); - 用 §5 表格给”莫奈 vs 莫奈 LoRA”各打三层分(0–2),和同学互评——训练你的风格分析之眼;
- 挑战:读 InST 或任意”单图风格反演”论文 §1,回答”反演和 LoRA 在数据需求/保真度上的取舍”。
8. 延伸资源
- Gatys 论文(A Neural Algorithm of Artistic Style)+ AdaIN 论文——两代定义之作
- 《StyTr2》等综述/后续——注意力时代的过渡(选读)
- 4.6 的 art-control-suite repo——第三代实操载体
8.4 面向艺术的生成:从控制工具到创作系统
本章定位:4.6 给了控制工具(LoRA/ControlNet/IP-Adapter),这一章讲如何把它们组织成面向艺术创作的系统——画家风格研究工作流、文化风格(水墨/工笔)的特殊性、画师协作管线,以及”美术学质检”的自动化。学完标准:能规划一个完整的 artist-study 项目(B1/B3 的执行手册)。
1. Artist Study:风格研究的完整工作流
“用 AI 研究一位画家”的标准管线(也是 B1 选题的施工图):
① 语料考据:画家存世真迹清单(博物馆开放接口优先,8.7)→ 筛高清、去印刷品翻拍
② 数据构建:80–200 张,统一分辨率,占位 caption("a painting by artist X")锁风格
③ LoRA 训练:rank 16–32(风格复杂度决定),lr 1e-4,每 500 步存档
④ 量化验收:三层打分(8.3 §5 表)——色相直方图 JS 散度 / 笔触特征余弦 / 构图类型分布
⑤ 迭代:形式层像了但构图不像 → 加构图 caption 标注重训;整体塑料感 → 查数据翻拍污染
⑥ 产出:LoRA 权重 + 验收报告 + 生成图集——一个可发表的作品集单元
关键认知:④ 的量化验收是这条管线的研究含金量所在——“生成图集”谁都能做,“复现度协议”是论文素材。
2. 文化风格的特殊性:水墨/工笔为什么难
水墨画的三个维度对生成模型都是硬骨头(8.1 §5 的伏笔在此兑现):
- 留白:负空间是构图本体,不是”没画的地方”——模型倾向把画面填满(训练数据以”满构图”的摄影为主);对策:caption 里显式描述留白比例与位置、构图 ControlNet 优先;
- 笔势的时序性:一笔的浓淡干湿是运笔过程的记录——静态像素丢失了速度与力度;这是”笔墨不可完全计算”(8.1)的模型侧印证,也是笔势生成研究的开放题(视频生成模型可能反而是对的工具——运笔过程本身是视频);
- 材料质感:宣纸渗透、绢本底色——低频色域微差,普通 LoRA 学不到;对策:高分辨率数据 + 局部 crop 增强。
工笔相对友好(勾线填色的程序性更强,线稿 ControlNet 天然契合)——“工笔易、写意难”是可以在你的数据集上定量验证的假说(B 线的又一个实验点)。
3. 画师协作管线:线稿上色的生产化
真实场景:画师给线稿 → 系统上色/风格化 → 画师修改。管线要点:
- 结构保真优先:lineart ControlNet 权重 0.8–1.0(宁可不改风格,不能改线);
- 风格层独立:画师指定的风格 LoRA + 弱化的 prompt 风格词(两层正交,4.6 的叠加规则);
- 局部重绘(inpainting)闭环:画师圈选不满意区域 → 只重绘选区 → 手稿节奏不被 AI 打断——“AI 出草稿、人做终审”的分工协议是这类工具能被画师接受的关键;
- 色彩规范注入:指定色板(IP-Adapter 色板参考或 prompt 色值约束)。
4. 生成图的”美术学质检”(可脚本化)
把 8.1 的判据做成自动体检脚本(art_qc.py,你 8.1 作业 2 的产品化):
| 检查项 | 判据 | 实现 |
|---|---|---|
| 明暗五调子完整 | 高光/反光/投影分布存在且物理一致 | 亮度分位数 + 梯度方向统计 |
| 视觉动线有序 | 显著性焦点 1–2 个,不在四角 | saliency 模型 + 连通域 |
| 色彩和谐 | 色环上呈已知和谐模式 | HSV 直方图 + 峰间距判定 |
| 留白比例(水墨) | 负空间占比在流派典型区间 | 阈值分割 + 形态学 |
| 细节密度梯度 | 主体区高频能量 > 背景 | FFT 分块 |
用法:批量生成的初筛(省人眼)+ 数据集质检(8.7)+ 论文里的自动指标。这张表本身就是 A3/8.1 映射表的产品化。
5. 一个完整案例的规划(“吴冠中式风景”)
作为 B1+B3 的示范项目书骨架:数据(吴冠中公开展出作品高清 150 张,占位 caption)→ 双 LoRA 实验(点线形式语言 vs 色彩构成,分开训再叠加——检验”风格可分解”假说)→ 构图控制(三分/留白 ControlNet)→ 验收(art_qc.py + 艺术背景同学盲评,8.7 协议)→ 论文点:风格分解假设 + 复现度协议。风险预案:单一画家数据量不足 → 退化为”风格族”(江南水乡系)研究——6.3 的降级思维。
6. 自测题
- artist study 六步里哪步含研究含金量?为什么?(量化验收——生成图人人会做,复现度协议是论文素材)
- 留白难的原因与对策?(训练分布偏满构图;caption 显式描述+构图控制)
- “笔墨的时序性”暗示哪个技术路线可能是对的?(视频/过程生成——运笔是过程不是结果)
- 画师接受 AI 工具的协议关键?(AI 出草稿人做终审 + 局部重绘不破坏手稿节奏)
art_qc.py的三个消费场景?(批量初筛/数据集质检/论文自动指标)- “工笔易、写意难”怎么变成实验?(同数据量训两类风格 LoRA,对比复现度——可定量检验的假说)
7. 动手作业
- 把 §1 工作流跑通前四步(任选公版画家,WikiArt 取数),产出首份验收报告;
- 实现
art_qc.py的前三个检查项,对你 4.6 生成的 20 张图出体检表; - 挑战:启动”双 LoRA 分解”实验(形式/色彩分开训),对比叠加与单独的效果——风格可分解性的一手证据。
8. 延伸资源
- 4.6(工具层)/ 8.3(风格理论)/ 8.7(数据与标注)——本章的三块地基
- 《The Art of LoRA》类社区经验帖——调参手感的民间智慧(当参照不当真理)
- 各博物馆开放接口——数据源头
8.5 艺术理解:让 VLM 真正"看懂"一幅画
本章目标:把 A1 假设(“VLM 语境层溃败”)变成实验方案——艺术理解的五个任务层、VLM 的真实能力边界、以及”领域微调 + 知识增强 + 看画 agent”三条提升路线的完整配方。学完标准:能搭出”看画 VLM”的 v1 实验管线。
1. “看懂”的五层任务(A1 的评测维度细化)
| 层 | 任务 | 示例 | 难度 |
|---|---|---|---|
| 描述 | 形式层 caption | “横构图,冷色调为主,笔触厚涂,三分法构图” | ★(VLM 已较好) |
| 分析 | 技法/构图推理 | “为什么伦勃朗光在这里有效:单侧三角亮区引导视线” | ★★ |
| 语境 | 归属与背景 | “从笔触与用色判断:印象派成熟期,约 1870s” | ★★★ |
| 图像学 | 符号解读 | “白鸽=和平;石榴=复活——宗教画的图像学传统” | ★★★ |
| 判断 | 评价/比较 | “与同题材学院派相比,此画的价值判断为何改变” | ★★★★(最主观) |
A1 的核心假设:主流 VLM 在描述层接近可用,分析层勉强,语境/图像学层系统性溃败(缺知识+缺推理),判断层则混淆”熟练话术”与”真实判断”。你的实验就是量化这个梯度。
2. VLM 看画的真实短板(跑分前预判,跑分后验证)
- 画家/流派细粒度混淆:印象派内部分得清莫奈/雷诺阿吗?——细粒度分类是 VLM 的经典弱区;
- 幻觉归属:没把握的画家也敢报名字(自信错误)——需要”拒答”机制评测;
- 形式层词汇贫乏:说不出”厚涂/罩染/干扫”等专业词汇(tokenizer 里都没多少艺术术语的中文对齐);
- 语境层无知识:不知道《夜巡》画于 1642 年——这不是”看”的问题,是”知道”的问题(→ 第 4 节 RAG);
- 长程推理缺失:从笔触推流派的多步推理链断裂(→ 5.1 的视觉 CoT)。
3. 路线一:领域微调(把”会用美术词汇”练进模型)
配方(2.5/3.2 方法的领域化):
- 数据:① WikiArt 元数据 → 模板化”流派/画家/年代”QA;② 强模型蒸馏:把”图+元数据”喂给 GPT-4o 级模型,产出”分析体”回答(先描述→再分析→后归属的 CoT 式结构);③ 你的 A1 v0 数据当留出评测(绝不混入训练);
- 训练:Qwen2.5-VL-2B + LoRA,1–3 万条,免费卡到 4090;
- 验收:A1 三层分数字 + 抽 20 例人评(和艺术背景同学合作——8.7 的人力教训);
- 预期发现(写成实验预期):描述/分析层显著提升;语境层若不配知识注入则提升有限——这个”有限”本身就是论文发现。
4. 路线二:知识增强(RAG——语境层的对症药)
语境层缺的是事实,看是看不出来的。管线:艺术知识库(画家年表/流派特征词条/名画解读,WikiArt 元数据+艺术史文本构建)→ 检索(CLIP 语义检索 + 元数据过滤)→ 拼入 prompt → VLM 回答。消融设计:微调 vs RAG vs 微调+RAG 的三层矩阵——预期”微调管词汇与格式、RAG 管事实”,两者正交互补。这个 2×2 矩阵就是一篇干净的分析文(C1 的完整落地)。
5. 路线三:看画 Agent(5.1 的 thinking-with-images 艺术版)
给 VLM 配三个工具:放大镜(裁剪局部再看——笔触判断必须看局部)、检索(查画家/流派知识)、对比(调出参考画并排)。流程:整体观察 → 假设 → 局部取证(放大笔触/签名/材质)→ 检索验证 → 结论。训练可以只做 prompt 工程(零训练成本)+ 少量工具调用轨迹的 SFT——C4 选题的最小实现。鉴别场景(真伪/真迹 vs AI 生成)是这个 agent 的杀手应用:A3 基准直接当评测场。
6. 实验管线的组合(一学期排期)
W1-2 A1 v0 评测集 300 条(8.7 的流程)+ 三个底座跑分 → 溃败梯度确认
W3-6 路线一微调(领域指令数据 2 万条)→ A1 复测
W5-8 路线二 RAG(与微调并行,2×2 矩阵)→ A1 复测
W9-12 路线三 agent(工具调用 + 20 例深度案例分析)→ 综合
产出 "三层溃败梯度 + 三条路线的分层修复矩阵" —— A1/C1/C4 三题连发
7. 自测题
- 五层任务里 VLM 的”假能力”最可能出现在哪层?为什么?(判断层——流畅的艺术话术≠真实判断;评测要设计”话术探针”)
- 语境层短板为什么”看”解决不了?(缺的是事实知识不是视觉感知——对症药是 RAG)
- 为什么 A1 数据”绝不混入训练”?(评测集进训练=自欺——3.7 陷阱 1 的自我防)
- 2×2 消融矩阵的两个维度和预期结论?(微调×RAG;词汇格式靠微调、事实靠 RAG、正交互补)
- 放大镜工具对哪类判断最关键?(笔触/材质/签名——局部证据,8.3 的形式层)
- 为什么留出集要”艺术背景同学人评”?(自动指标测不了判断层的真实性——8.7 的人力教训)
8. 动手作业
- 构造 200 条”艺术指令数据”(WikiArt 模板 QA 100 + 蒸馏分析体 100),完成路线一的第一次 LoRA 微调;
- 在 A1 v0 上出”底座 vs 微调”的三层分数对比表;
- 给 RAG 管线写个 50 行原型(FAISS + 词条库),测 20 道语境题的前后对比;
- 挑战:用放大镜 agent 模式(纯 prompt)跑 A3 的 20 张 AI 生成图鉴别,记录成功/失败案例——C4 的第一页素材。
9. 延伸资源
- AQUILA / ArtCoT 类艺术 VLM 基准(检索最新)——同赛道参照
- LLaVA 系列的多轮工具扩展(Scaffolding 类工作)——agent 路线的工程参照
- 《视觉艺术图像学》入门读物——图像学层的标注弹药(配合 8.1)
8.6 AIGC 时代的艺术评价与人类偏好对齐
本章目标:回答”生成模型变强之后,谁来定义好看”——自动指标的失效史、偏好奖励模型的技术栈、扩散模型的 RLHF/DPO 对齐,以及奖励被钻空子后的”AI 工业感”。这是 8.2(美学评分)的续篇与 E1 选题的完整图纸。学完标准:能画出文生图对齐的全链路,能手做一个”奖励钻空子”实验。
1. 评测的失效史:为什么需要学习型指标
- FID/IS 时代:比较生成分布与真实分布的统计距离——和人类判断相关性弱(构图平庸但统计上”像真图”就能拿高分);
- CLIPScore 时代:图文一致性有了代理指标——但它测”像不像 prompt”,不测”好不好看”;
- 人类偏好模型时代(2023– ):直接学”人觉得哪个好”。代表与数据:ImageReward(人类标注的成对偏好)、PickScore(Pick-a-Pic 百万级真实用户偏好)、HPSv2(专家偏好,覆盖绘画/照片/概念艺术多域)。训练配方就是 8.2 §3 阶段三那套:CLIP/VLM 底座 + Bradley-Terry 成对排序损失——8.2 的美学评分与 2.7 的 DPO 在此会师。
链条全景:人类偏好数据 → 奖励模型 → 三个用途(生成模型选型评测 / 推理时最佳 n 选一 / 训练信号驱动 RLHF/DPO)——第三条就是本节主题。
2. 扩散模型的偏好对齐:三代方法
- DDPO(2023):把扩散采样看成多步 RL 过程(每步去噪=动作),奖励模型打分,PPO 更新——第一代证明”可行但贵”;
- AlignProp / DPOK:反向传播直接穿过采样链(可微奖励微调)/ KL 正则版 RL——工程简化;
- Diffusion-DPO(2024– ):2.7 的 DPO 直接平移——成对图像偏好(同 prompt 两图)+ 文本侧对称公式,绕开奖励模型在线打分,稳定性最好,SD3/FLUX 时代的工业主流。
与前文的闭环:你已在文本侧学过 DPO(2.7)、在美学侧学过偏好建模(8.2)——扩散侧只是把”回答偏好”换成”图像偏好”,数学骨架完全同构。
3. 奖励钻空子:AI 工业感的动力学解释
8.2 §5 遗留的问题在此得到机理解释:“技术好但艺术差”(平均脸、过度饱和、塑料质感)不是偶然,是对奖励模型的过优化:
- 美学奖励学到的人类偏好有系统偏差(高饱和度、高对比、中心构图在众包数据里更容易赢);
- 生成模型沿着奖励梯度走 → 把偏差放大到极端 → 分布坍向”奖励模型审美”,多样性丧失(GAN 模式坍塌的 RL 版);
- 文本对齐奖励同理:CLIPScore 优化过头 → 出现对抗性图案(图里藏文字骗 CLIP)。
这就是为什么 E1 选题(中式审美奖励模型)有价值:现有奖励模型的偏差是西式众包偏好——换一批人做标注,就是在给生成模型换审美坐标系。同时必须配”多样性保持”约束(KL 到参考分布——2.7 的 KL 缰绳在扩散侧同样救命)。
4. 评价体系的分解(比”一个总分”正确的做法)
一个成熟的生成评测应拆成正交的三轴(写论文时这决定了你的实验矩阵):
- 指令遵循:prompt 里的元素/属性/空间关系是否实现(VQAScore/T2I-CompBench 类);
- 美学质量:8.2 的 NIMA/美学奖励模型;
- 人类偏好:HPS/PickScore + 小规模真人盲评(金标准)。
关键认知:三轴会冲突(过度优化美学 → 遵循度下降)——帕累托前沿的形状本身就是研究内容(“加多少美学奖励,牺牲多少遵循度”——E1/E2 的实验设计核心)。
5. 学生实验配方(一个周末)
- 奖励钻空子演示(最快见效):拿公开美学奖励模型当目标,对 SD1.5 跑 500 步 DDPO/AlignProp(开源实现现成),对比优化前后的图与奖励分——亲眼看到分数涨、图变塑料;
- 奖励模型小训:Pick-a-Pic 子集(10 万对)+ open_clip ViT-B/16 + BT 损失,训 PickScore-mini(8.2 作业的升级版),测与人类排序的 SRCC;
- 跨文化探针:用你的 mini 模型给”水墨画 vs 油画”同构图打分,量化偏差(E1 的动机数据);
- 产出:
reward-hacking-labrepo——三个实验+一张”奖励分 vs 多样性”的散点图。
6. 自测题
- FID 为什么和人类判断脱节?(统计距离不含构图/语义/美学——“统计像”不等于”好看”)
- PickScore 的数据从哪来?为什么比人工标注好?(真实用户成对选择;规模+真实分布场景)
- Diffusion-DPO 相比 DDPO 赢在哪?(绕开在线奖励打分,纯监督式训练——2.7 的 offline/稳定逻辑)
- “AI 工业感”的动力学成因链?(偏好偏差→梯度放大→分布坍缩——RL 版模式坍塌)
- 三轴评测为什么必须正交拆解?冲突怎么用?(单总分掩盖权衡;帕累托前沿形状即研究内容)
- E1 换标注人群的真正意义?(重定义奖励坐标系的偏差方向——生成模型审美的”立法权”)
7. 动手作业
- 完成第 5 节三个实验,重点把”奖励分↑ vs 图变差”的对照图做好(这是面试与答辩时的最强一图流);
- 用 HPSv2 给 SD1.5/FLUX/你 4.6 的风格 LoRA 各打 20 张图的分,观察”风格化是否被偏好模型惩罚”——B 线选题的数据点;
- 精读 Diffusion-DPO 论文(6.1 三遍法),画它与 2.7 文本 DPO 的公式对照表;
- 挑战:设计”多样性保持”的一个具体约束(KL 系数/批次内多样性正则),在实验 1 上验证它能否缓解塑料化——E1 的方法章雏形。
8. 延伸资源
- ImageReward / PickScore / HPSv2 论文——偏好模型三连(8.2 已列,此处精读训练细节)
- DDPO → Diffusion-DPO 论文链——对齐方法演化
- Pick-a-Pic / HPD 数据集页——偏好数据长什么样
8.7 艺术数据集与基准构建:从 WikiArt 到自建
本章目标:给你 A1(看画基准)/D1(中国画数据集)的完整施工手册——现有资源盘点、标注规范怎么写、质量控制怎么做、版权怎么处理。学完标准:能独立启动一个”30 条样例 → 300 条试点 → 3000 条成集”的数据集项目。
1. 现有资源盘点(先看别人修好的路)
| 数据集 | 规模/标签 | 特点与坑 |
|---|---|---|
| WikiArt | 25 万件/流派·画家· genre 标签 | 最大最常用;标签噪声大(流派边界粗糙)、中国画几乎缺位、高清率参差 |
| ArtBench | 6 万张/10 流派(含浮世绘) | 类平衡、抓取干净——做分类基线的首选 |
| DeviantArt/ArtStation 类 | 现代数字插画/二次元 | 风格多样但版权最敏感,研究慎用商用 |
| 博物馆开放接口(Met、Rijksmuseum、SMK 等) | 馆藏级高清+权威元数据 | 版权最干净、元数据最专业;规模有限、西方中心 |
| 中国画专项 | 零散(各馆数字化、学术项目) | 系统性空白——D1 的机会所在 |
盘点结论:通用分类有得用,“理解与评测”层的数据几乎空白——没有按三层框架标注的 VLM 评测集、没有中国画系统性数据、没有”风格复现度”的量化基准(8.3 作业的延长线)。这就是 A1/D1 的空间。
2. 数据集的三种形态(决定你的工作量与论文形态)
- 分类集(ArtBench 型):标签+图,标注成本低——适合练手;
- 评测基准(A1 型):题干+选项/参考答案+判分协议——每道题都是一次小标注工程,成本高但学术杠杆最大;
- 资源集(D1 型):图+多维标注+规范文档——长期资产,师生共建的最佳载体。
3. 标注规范怎么写(v0→v1 的迭代法)
先写规范再标图(顺序错了返工十倍)。规范必含五节:
- 分类学:三层框架落地为字段——形式(流派/媒介/色彩性格/构图类型)、内容(题材/主体/叙事要素)、语境(画家/年代/流派归属/图像学符号);每个字段给封闭枚举+图例(“写意”与”兼工带写”的分界,文字说不清就放两张对比图);
- 判定规则:边界 case 的优先级(“画家标注冲突时以馆藏元数据为准”);不确定性选项(允许”存疑”,禁止硬选——硬选出来的标签是毒数据);
- 样例集:30 条”金标准”样例(含正例/边界例/反例),标注员先通过样例测试才能上岗;
- 流程:标注→抽检→仲裁三级;每批次 10% 双人背靠背标注算一致性;
- 版本:v0 试点(300 条)→ 一致性分析 → 修规范 → v1 放量。
4. 质量控制的三把尺
- 标注者间一致性(IAA):分类字段用 Cohen’s kappa(≥0.6 可接受,≥0.8 优秀);低一致性的字段不是标注员的错,是你分类学的错——回去切分枚举或加图例;
- 锚点抽查:混入 5% 金标准样例,实时监控每个标注员的准确率漂移;
- 模型交叉核查:用 VLM/CLIP 预标注 + 人工复核(人机协同提效),但模型只能提议不能终审——否则模型的偏见会写进你的数据集(3.7 的污染思想在供给侧)。
5. 版权与伦理(学术研究也要干净)
- 公有领域(作者逝世 70 年+,大部分古典绘画)作品的摄影复制品:馆藏机构对”摄影化”可能主张权利——用博物馆开放接口的条款(多数 CC0/CC-BY)最稳;
- 在世艺术家:训练用途避开,评测/引用需授权或合理使用论证——论文里写清数据来源与用途限定(datasheet 必填项);
- 人物肖像的隐私、宗教/民族题材的文化敏感性——D1 尤其注意。
6. 自建项目时间线(A1/D1 通用)
第1-2周 规范v0 + 30条金标准样例(和导师过一次)
第3-4周 300条试点 → kappa分析 → 规范v1
第5-8周 3000条放量(双人背靠背10%)→ 清洗 → datasheet v1
第9-12周 基线实验(2-3个VLM跑分)→ 数据集论文或并入A1
成本真相:120 小时标注人力 ≈ 导师组里 1–2 个本科生同学合力一学期——这就是为什么要早进组(数据工程是组内人力能办的事,独自一人会卡死在放量期)。
7. 自测题
- 三种数据集形态的成本/杠杆排序?(分类<资源<评测基准;杠杆反序——评测基准最贵也最值)
- “低一致性字段回去改分类学”为什么是对的?(kappa 低多数源于枚举边界含糊,不是标注员水平问题)
- 模型预标注为什么只能提议不能终审?(模型偏见会系统性写进数据——供给侧污染)
- “存疑”选项为什么必须存在?(禁止硬选——一致性指标被虚假抬高,毒数据入场)
- 为什么用博物馆开放接口优于网页抓取?(条款干净+元数据权威——版权与质量双保险)
- datasheet 必填哪三类信息?(来源与授权/标注协议与一致性/已知局限)
8. 动手作业(A1/D1 的第一步)
- 下载 WikiArt 的元数据(标签分布统计脚本),写 300 字”坑点报告”(流派标签噪声实例 3 个);
- 给 A1 写三层标注规范 v0(每层 5 个字段+枚举+30 条样例里的 10 条);
- 算一次 kappa:和同学各自标同 40 张画的”色彩性格”字段,对比一致性——亲手体验”分类学错了别怪人”;
- 挑战:给 Met 开放接口写个抓取脚本,拉 50 张高清中国/日本馆藏——感受”干净数据”的手感。
9. 延伸资源
- ArtBench / WikiArt 原始论文——现有基准的设计得失
- Datasheets for Datasets(Gebru et al.)——数据集文档的标准格式
- Met/Rijksmuseum Open Access API 文档——干净数据的源头
8.8 文化遗产数字化与数字人文:AI 进博物馆
本章目标:把”文化遗产 + AI”从情怀变成一套技术栈与合作路径——数字化管线、VLM 的四个用武之地、数字人文的研究范式,以及学生切入的正确姿势。这是 D4 选题的施工手册,也是你方向里”社会价值叙事”最强的一章。学完标准:能设计一个博物馆合作课题的雏形。
1. 管线全景:从文物到知识服务
采集:高清摄影 / 结构光扫描 / 多光谱成像(HSI,可 revealing 底稿与修改痕迹)
↓
重建:photogrammetry → 3DGS(5.5 的技术在文物上的主战场)
↓
编目:元数据著录(Dublin Core 等标准;CIDOC-CRM 概念层)——传统上纯人工,最贵的一环
↓
增值:VLM 自动描述 / 断代与流派辅助判断 / 题跋 OCR 与翻译 / 知识图谱(画家-流派-题材-流传链)
↓
服务:数字展厅(可漫游 3D)/ 智能导览 / 教育内容生成
VLM 的机会集中在”编目”和”增值”两环——这是博物馆界公认的人力瓶颈(一座省级馆藏品数十万件,编目积压以十年计)。“AI 编目员”的真实需求是本方向与纯学术题的最大区别:有人真的会为它付钱。
2. VLM 文物编目的任务分解(D4 的技术内核)
- 结构化著录:从图像+已知信息生成规范条目(名称/题材/材质/尺寸/保存状态)——本质是”受控词表约束下的 VQA”,VLM 微调即可起步(8.5 路线一);
- 辅助断代与归属:流派/年代特征判断——只做”辅助+置信度”,终审权永远在人(博物馆的学术责任不可能交给模型);
- 题跋印章处理:书法 OCR(2.2 的 tokenizer 问题在这里变难——异体字/草书)+ 印章检测与归属 + 诗文与画面的语义关联(D2 选题);
- 多光谱 × AI(前沿):HSI 揭示的底层草图/颜料成分,用分割/分类模型做颜料制图——AI for Science 与文化遗产的交叉,数据稀缺但论文含金量高;
- 数字修复辅助:inpainting 补全缺损 + 风格一致性约束——伦理红线:只能用于”虚拟复原展示”,实体修复与档案记录必须保留真实状态(威尼斯宪章精神:可识别、可逆、不臆造)。
3. 数字人文(Digital Humanities):另一个发表世界
- 范式:用计算方法回答人文学科的问题——不是”把图喂给模型”,而是**“量化艺术史”**:十万件藏品的构图复杂度随朝代如何演化(8.1 映射表的规模化应用)、某母题(如”渔隐”)在明清的数量地理分布、色彩使用与社会经济波动的相关……
- 方法形态:CLIP/VLM 嵌入做大规模” distant viewing”(远读)+ 统计检验——算力友好(推理为主),非常适配学生;
- 发表生态:数字人文期刊/会议(中文核心、《数字人文》期刊、ADHO 系)与 CS 会议是两个世界——前者重问题的人文学意义与方法的恰当性,不卷 SOTA;与艺术学院/人文学院合作者的价值在此最大化。
4. 中国场景与切入路径
- 标杆:数字敦煌(全球典范——高精度采集+开放素材库)、故宫数字文物库、各大省博的数字化工程——说明上层需求真实且持续;
- 学生的现实路径:① 公开数据先行(Met/SMK 开放接口、数字敦煌素材库)做方法原型;② 带着原型找合作(导师的博物馆关系、或从地方中小馆切入——大馆门槛高但小馆的编目需求更迫切);③ 发表走”数字人文 + CS workshop”双轨;
- 避坑:别用”我要用 AI 颠覆文博”开场——文博界对技术傲慢极其敏感;正确的开场是”我读了贵馆的数字化年报,注意到编目积压问题,我的工具在公开数据上做到了 XX”。
5. 自测题
- VLM 机会集中在管线哪两环?为什么?(编目与增值——人力瓶颈且有人付费)
- “辅助断代”的边界怎么定?(只给置信度建议,终审在人——学术责任不可外包)
- 数字修复的伦理三原则?(可识别/可逆/不臆造——虚拟展示与实体修复分离)
- 数字人文与 CS 会议的评审偏好差异?(人文意义与方法恰当性 vs SOTA 与技术新颖性)
- HSI+AI 是什么、难在哪?(多光谱揭示底稿颜料,AI 做颜料制图;数据稀缺——高含金量前沿)
- 与博物馆合作的开场公式?(读年报→点名具体问题→公开数据上的原型证明——反技术傲慢)
6. 动手作业
- 用数字敦煌/Met 开放数据拉 100 件藏品,做一个”VLM 自动编目”原型(受控词表 prompt + 结构化输出),人工核对 30 条的准确率;
- 找一篇《数字人文》期刊的论文精读(6.1 模板),对比它的写作与 CVPR 论文的范式差异——写 300 字;
- 给 D4 写一页 proposal:目标馆型/数据获取路径/最小可行产品/发表双轨计划;
- 挑战:设计”风格演化远读”实验(用 8.1 映射表的特征 + WikiArt 年代标签,画 1800–1920 印象派前后色彩/构图的量化演变曲线)——这就是一篇数字人文论文的骨架。
7. 延伸资源
- 数字敦煌素材库 / Met Open Access / 故宫数字文物库——数据源头
- 《数字人文》期刊 / ADHO(ALLC/ACH)——发表生态
- CIDOC-CRM 入门文档——文物元数据的概念模型(选读)
8.9 交叉选题库:结合导师方向的 20 个可执行题目
使用方式:这不是让你选一个”最酷”的,而是带着这张表去和导师对资源——组里有标注数据、有艺术学院合作者、有某领域行业关系的,对应题目优先级立刻上升。每题标注:算力档(①免费卡 ②单张4090 ③多卡/A100)、周期、交付物。 难度标尺:★=课程级可完成,★★=workshop/会议短文,★★★=主会冲刺(需进组资源)。
A. 评测与基准(算力最省,学术杠杆最高)
A1(★★)VLM 看画三层次基准:构造”形式/内容/语境”三层评测集(8.1 框架直接变成标注维度),测主流 VLM 各层通过率。假设:语境层全面溃败=机会。|①|2 月|数据集+评测报告 A2(★★)美学奖励模型的流派偏差:PickScore/HPS 在不同文化/画种上的分数偏移量化(同构图画种互换重打分)。|①|1 月|偏差分析文 A3(★★)AI 图 vs 人类画的鉴别基准:8.1”五调子/笔触/动线”特征工程 + 分类器,并测 VLM 的鉴别力。|①|1.5 月|基准+特征分析 A4(★★★)构图质量的注意力分析:用 DiT/DiT 的 cross-attention 热图与”构图焦点/动线”的美术学标注做对齐度研究——“模型心里有没有构图”。|②|3 月|可解释性论文
B. 生成与控制(接 4.6,出视觉结果,展示性最强)
B1(★)画种风格 LoRA 系统评测:多画种×多 rank 的复现度量化(4.6 作业的扩展版:色相直方图/笔触特征/专家盲评)。|②|1.5 月|评测协议+repo B2(★★)线稿上色的风格保真:ControlNet+LoRA 叠加下”构图保真 vs 风格保真”的权衡曲线与可控旋钮。|②|2 月|方法短文 B3(★★)构图可控生成:以显著性图/三分法热图为条件的生成控制——把”构图法则”变成可注入条件(saliency-ControlNet)。|②|2.5 月|方法文 B4(★★★)诗画互译:中文诗→画的生成与评价(意象→视觉的映射基准+微调),文化计算浓度最高的题。|②③|3 月+|数据集+模型
C. 理解与知识(VLM+艺术知识,接卷3/卷5)
C1(★★)艺术知识增强 VLM(RAG):画家/流派/年代表知识库挂 VLM,测语境层问答提升(对 A1 的溃败做补强实验)。|①②|2 月|系统+报告 C2(★★)图像学符号理解:iconography(橄榄枝=和平之类)的符号-语义 benchmark,测 VLM 的文化符号盲区。|①|1.5 月|基准 C3(★★★)流派归因的可解释性:Grad-CAM/attention 与 8.1 形式层特征(笔触/色域)的相关性分析——让归因”说美术学的话”。|②|3 月|可解释性论文 C4(★★)多轮艺术评论 Agent:VLM+工具(检索/放大局部/查数据库)的看画对话 agent——5.1 thinking-with-images 的艺术版。|②|2.5 月|agent 系统
D. 数据与人文(与艺术学院合作的最佳接口)
D1(★★)中国画数据集与标注规范:画种/画家/题跋/印章四字段,标注指南+质量协议(8.1 指出 WikiArt 中国画是短板——空白即机会)。|①②|2-3 月|数据集+ datasheet D2(★★)题跋印章的图文关联:书法 OCR+印章检测+与画面的语义关联(诗书画印一体的多模态本体)。|②|3 月|pipeline+分析 D3(★)美学评分的跨文化对比:同一批图在 NIMA/人类中式审美标注上的分差与特征归因。|①|1 月|分析短文 D4(★★★)文化遗产数字化管线:藏品摄影→3D/增强→VLM 自动描述与知识挂接的端到端 demo(博物馆合作则升★★★+)。|②③|3 月+|系统+案例研究
E. 组合拳(热门引擎×你的领域,接 5.1/8.2/8.6)
E1(★★★)美学偏好奖励模型用于文生图 DPO:自建中式审美偏好对 → 训练奖励模型 → DPO 微调文生图——8.6 的完整闭环。|③|3 月+|方法论文 E2(★★)小模型美学 RL:2B VLM + GRPO 学美学评分(可验证奖励=与人类排序一致度),8.2×5.1 交叉。|②|2.5 月|方法短文 E3(★★★)看画 agent 的过程奖励:5.1 的过程监督用到”先观察局部再综合”的看画推理上。|③|3 月+|会议冲刺 E4(★★)美术史苏格拉底教学 Agent:VLM+课程知识库+追问式对话,教育场景应用(好发、实用、展示性强)。|②|2 月|系统+用户研究
选择决策树
- 组里有标注人力/艺术合作者 → D 线优先(数据是长期资产,导师最认);
- 组里算力紧张、要快出成果 → A1/A2/A3(免费卡,1-2 个月见论文坯子);
- 组里有生成模型基础/想蹭 AIGC 热度 → B 线或 E1;
- 你想练 RL/推理引擎(卷5.1 路线)→ C4/E2/E3;
- 所有题目的共同底座都是 A1 的数据集——先做 A1,全线受益(这是最稳的战略建议)。
和导师谈时的三句话框架
“我整理了 20 个交叉方向的题目,分四类:评测基准、生成控制、理解知识、数据人文。考虑到咱们组的【数据/合作/算力】资源,我建议从【X】切入,先花【N 周】做出【具体交付物】。这是我目前能力的证明(甩 repo 链接)。“——具体、可拒绝、带证据。
自测题
- 为什么 A1 是全线底座?(评测数据集是其他所有题目的基础设施——B/C/E 都要用它做验收)
- 数据题(D 线)对导师的独特价值?(长期资产+师生共建+学科交叉的立项叙事,比一篇论文的长期价值高)
- 算力档①的题目共同点?(评测/分析/轻微调——推理为主训练为辅)
- 从”课程级★“到”主会冲刺★★★“差的通常是什么?(数据规模、系统完整度、以及一个严格的消融与对比矩阵——不是更炫的方法)
动手作业
- 把这 20 题抄进你的台账,按”导师资源/我当前能力/兴趣”三列打分,选出 top3;
- 为 top1 写一页纸 proposal(2.10 §6 的模板)——下次导师面谈的弹药;
- 给 A1 画三层评测集的 v0 标注规范(30 条样例即可)——这是本周就能开始的事。
9.1 九个月周级执行计划(2026.10 – 2027.06)
使用方式:打勾制。每周日花 10 分钟填”复盘模板”。弹性原则:落后两周以内属正常,处理方式不是补作业而是直接跳到当前周——计划和列车一样,错过一班搭下一班。学期中每周 15–20 小时(平日晚上 2h × 3 + 周末两个半天),寒暑假全职。
阶段一:基础(W1–W6,2026.10.05 – 11.15)
- W1–W2:读 0.1 数学基础 + 0.3 反向传播从零实现;完成两章的动手作业(NumPy softmax 推导验证;micrograd 引擎跑通)。配套:3Blue1Brown 线代/微积分本质各刷一遍。
- W3–W4:读 0.2 PyTorch 实战;跑通 CIFAR 训练脚本;完成作业(ResNet-18 ≥93% + wandb 接入)。
- W5–W6:读 0.4 训练工程常识,给脚本装”四件套”(seed/checkpoint/clip/单batch过拟合);读 1.1 CNN。
- W6 里程碑:GitHub 上第一个像样的 repo(ResNet 复现 + 训练分析 README)。
- ⚠️ W5–W6:开始联系导师(模板见文末)。不要等”准备好”——你现在已经有能聊的资本了。
阶段二:现代 CV(W7–W12,2026.11.16 – 12.27)
- W7–W8:1.2 注意力机制(手写 + 对拍 + 可视化);1.3 Transformer 拆解(写好后来点单)。
- W9–W10:1.4 ViT、1.5 自监督概念(MAE/CLIP/DINO 泛读)。
- W11–W12:1.6 CLIP 复现项目(zero-shot 评测小报告)+ 1.7 SAM 会用。
- 同步:读 8.1 美术学基础,按 8.1 第 10 节的 10 个问题和导师完成第一次正式谈话;参加组会旁听。
- W12 里程碑:CLIP 项目 repo + 与导师确定进组形式(文献调研起步)。
阶段三:LLM 内功(W13–W20,寒假 2026.12.28 – 2027.02 底)
- W13–W15:卷2.1–2.3(tokenization + nanoGPT 逐组件)——跟 Karpathy 视频逐行敲。
- W16–W17:卷2.4–2.5(预训练概念 + SFT);跑通 LLaMA-Factory 的第一次微调。
- W18–W19:卷2.6–2.7(LoRA/QLoRA + DPO/GRPO 原理);寒假主项目:LoRA 微调一个 7B 垂直模型并上传 HF/魔搭。
- W20:卷2.8 推理(vLLM 部署自己的模型);卷2.9–2.10 泛读。春节前后正常中断,别焦虑。
- W20 里程碑:HF/魔搭上有一个你的模型页 + nanoGPT repo。这个寒假是整个计划中性价比最高的二十天。
阶段四:多模态主战场(W21–W30,大三下 2027.03 – 05 中)
- W21–W24:卷3 VLM(3.1–3.3 + 3.5 开源双雄报告精读);复现 LLaVA 式两阶段训练。
- W25–W28:卷4 生成模型(4.1–4.5 主线 + 4.6 可控生成实操)。
- W29–W30:垂直领域 VLM 项目收尾(建议直接长在导师的方向上:比如艺术/美学领域 VLM——8.2 章第 5 节的课题方向)。
- ⚠️ 并行(5 月前必须完成):夏令营材料包(清单见下);和导师确认推荐信。
- W30 里程碑:LLaVA 复现 repo + 垂直 VLM 项目 + 材料包齐备。
阶段五:科研冲刺(W31 起,2027.05 中 –)
- W31–W33:夏令营投递(目标梯度:冲刺 2 所 + 匹配 3 所 + 保底 2 所);卷5 按兴趣选读(建议 5.1 多模态推理 RL 优先)。
- 暑假 W34–W40:进组科研或大厂多模态实习;每周精读 2–3 篇 arXiv(用 6.1 三遍法);选 1 篇做最小复现。
- 大四上:预推免/秋招/毕设选题——毕设 = 把暑假的复现项目升级成小研究,一份工三份收获。
夏令营材料清单(5 月前逐项打勾)
- 成绩单 + 排名证明(教务处开,提前办)
- 个人陈述(结构:动机 → 准备了什么(GitHub 链接)→ 想做什么方向 → 为什么是这个组)
- 简历一页(项目经历 = 你的三个 repo,每条写”做了什么 + 数字结果”)
- 导师推荐信(W6 就要开始铺垫,W12、W20 各汇报一次进度,5 月开口时水到渠成)
- 英语:六级成绩(不够就暑假补)/ 有余力考个雅思
- 获奖证明扫描件
给导师的第一条消息(模板)
老师您好!我是软件工程 20XX 级学生 XXX,GPA 排名 X/XXX。我最近半年自学了深度学习并完成了几个实践项目:从零实现了神经网络训练引擎、复现了 ResNet 和 CLIP(附 GitHub 链接:xxx)。拜读了您 XXX 方向的工作(提一篇具体论文 + 一句你的理解),非常希望能在您课题组学习和承担文献调研、实验复现等工作。请问这学期是否方便约 20 分钟当面请教?
要点:具体作品链接 > 一切形容词;提到对方某篇论文证明你不是海投;明确你能干什么(调研/复现);时间诉求小(20 分钟)。
每周复盘模板(存成一个 md,每周追加三行)
## W7 (11.16–11.22)
- 完成了:手写 attention 并与 PyTorch 对拍通过
- 卡住了:多头 reshape 顺序搞反,卡了 2 小时(已写进卷7)
- 下周:Transformer block 组装 + ViT 论文精读
每月加一行”回头看”:这个月我能给别人讲清楚什么?讲不清楚的就是假学会。
三条弹性原则
- 落后不补课:直接跳到当前周,落下的章节标记为”泛读”往后带;
- 导师的事永远优先级最高:组会任务 > 本计划,进组后本计划自动服务于组里方向;
- 算力不够就降级实验:7B 降 2B,全量降 LoRA,大 epoch 降小 epoch——实验设计能力比实验规模重要。
9.2 保研 / 考研 / 留学 / 就业:四条路的真实分析
本章目标:基于你的画像(软工大三、目标多模态大模型、偏科研、导师方向美术学交叉)把四条路的成本、门槛、适配度摆到一张桌上。共同前提:本笔记路线产出的作品集(repo/数据集/复现报告)对四条路全部有效——一次建设,四处可用。 ⚠️ 政策与行情每年变,本章给的是决策框架与量级感,具体数字以当年官方信息为准。
1. 保研(推免)——科研路径的默认最优解
机制:夏令营(5–7 月)→ 预推免(9 月)→ 十月正式推免。拼三样:成绩排名(硬门槛,夏令营入营线常见前 10–30% 因校而异)、科研经历(进组产出、论文加分)、作品集与面试表现。
对你的适配:★★★★★。理由:① 你已按 9.1 在铺垫导师(W5–W6 动作),本校组的关系是保底盘;② 多模态是热门,985/科研院所(中科院系)名额多;③ 选导师 > 选学校(做研究的人,方向和导师匹配度决定读研质量)。
风险与对策:排名不够线 → 用竞赛/论文/大厂实习背书申请破格;本校无合适方向 → 夏令营广撒网(冲刺 2 + 匹配 3 + 保底 2,9.1 的梯度表)。
2. 考研——用一年时间换一次重开
成本:数学+英语+政治+408(或院校自命题),有效备考约 10 个月全职——意味着放弃一段科研窗口期。回报:进入更好的平台重开。
对你的适配:★★★(保研不稳时的主选)。要点:① 初试纯应试,本笔记路线帮不上初试,别自我感动地”边备考边搞科研”;② 复试才是作品集的提款机——面试官看到”复现过 LLaVA + 有微调模型 + 有数据集项目”的考研生,和只背了八股的考研生,是两个物种;③ 学硕(研究导向)与专硕(工程导向)的选择:想读博选学硕,想就业专硕也不吃亏(大模型行业不太区分)。
策略:大三下把 9.1 计划走完(作品集成型),暑假后全职备考——科研与备考的时间划分要狠。
3. 留学——科研浓度最高,也最贵
路径:授课硕士(一年制,就业导向)vs 研究型硕士/PhD(科研导向)。做多模态科研的正路是 PhD,而 PhD 申请的硬通货排序:科研经历与论文 > 推荐信(科研推荐人)> 套磁匹配 > GPA > 语言成绩(GRE 在多数项目已弱化/可选)。
对你的适配:★★★(家庭条件允许 + 科研心极强时优先)。要点:① 北美(CMU/UMich/UIUC/UCSD 系的多模态组)、欧洲(ETH/EPFL/Tübingen,岗位制博士有工资)、港新(NUS/NTU/HKUST,离家近节奏快)三类各有生态;② 申请 PhD 本质是找工作——套磁信 = 你 8.9 的 proposal 思路 + 导师近期论文的具体回应;③ 时间线比保研长一年(申请季在大四上),本笔记的产出恰好铺满申请材料。
4. 就业(AIGC/大模型岗)——最快变现,波动最大
岗位地图(2026 视角):多模态算法工程师(VLM 微调/评测——与本笔记路线重合度 90%)、生成算法(4.x 技能栈)、大模型应用/Agent 工程(RAG/工具调用,门槛较低需求量大)、推理 infra(卷7 方向)、数据工程(5.2,隐性刚需)。
对你的适配:★★★(若科研心不坚定,这是合理选项)。要点:① 校招算法岗竞争激烈,项目 > 实习 > 论文(工程岗逻辑);大模型应用岗更看重工程交付能力;② 实习转化是主通道——大四上去多模态团队实习(字节 Seed/阿里通义/快手可灵/智谱等,9.1 列过)比海投有效;③ 行业波动风险要认清:算法岗供需比逐年恶化,infra/应用侧更稳——作品集里”能部署、能交付”的项目(2.8 的 vLLM 服务)比纯刷点项目抗跌。
5. 决策树(按当前信息先选主路,保留 20% 调整权)
GPA 排名在保研线内?
├─ 是 → 保研主路(现在就执行 9.1 的导师铺垫)
│ └─ 心里有留洋梦 → 研究生期间再申 PhD(科研产出带得走)
└─ 否 → 家里支持 ≥3 年 + 科研心强?
├─ 是 → 考研(作品集留到复试)或 直接准备申请 MS/PhD
└─ 否 → 就业主路:大四上实习 + 校招,走大模型应用/工程岗
三条通用建议:① 别在歧路上耗太久——大三下结束(2027.6)是决策截止线,此前保研准备与作品集建设对四条路都不亏;② 四条路的「第一步」高度重合(把 9.1 走完)——这就是为什么不必现在焦虑;③ 家庭会议早开:留学/考研的成本问题不是你一个人能定的。
6. 自测题
- 保研拼的三样东西与你的准备进度?(排名—GPA 现状;科研—进组;作品集—本笔记路线)
- 考研路线里本笔记路线在哪个环节变现?(复试——作品集对面试官的降维打击;初试帮不上)
- PhD 申请的硬通货排序?(论文/科研 > 推荐信 > 套磁 > GPA > 语言)
- 就业岗”项目>实习>论文”的逻辑和什么岗相反?(研究岗/PhD 录取——论文权重最高)
- 为什么”大三下结束是决策截止线”?(此后各路径开始分叉:保研材料/考研全职/实习入职——共同准备期结束)
- 你 8.9 的 A1 数据集对四条路分别怎么用?(保研面试素材/考研复试作品/申请套磁附件/校招项目经历——一次建设四处可用)
7. 动手作业
- 查你学校近三年保研线和你当前排名,写三行结论(主路判定);
- 列 3 个目标院校/组的导师名单(多模态方向),各写一句”他的哪篇工作与我方向相关”(8.9 的功课直接复用);
- 家庭会议提纲一页:各路径成本量级 + 你的主路建议 + 需要家里决策的点;
- 把决策树的结果写进 9.1 计划的 W31 里程碑处。
图解 · 四条路决策树(Mermaid 版)
flowchart TD
A["当前排名在保研线内?"] -->|是| B["保研主路<br>立刻执行 9.1 的导师铺垫"]
A -->|否| C{"家庭支持 ≥3 年<br>且科研心强?"}
C -->|是| D["考研(作品集留到复试)<br>或 出国申请 MS/PhD"]
C -->|否| E["就业主路<br>大四实习 + 校招"]
B --> F{"心里有留洋梦?"}
F -->|是| G["研究生期间再申 PhD<br>(科研产出带得走)"]
F -->|否| H["安心读研,深耕方向"]
D -. "无论哪条:9.1 计划的产出全部通用" .-> B与正文 §5 的决策树同构——放在这里是提醒你:决策树的四个叶节点,共享同一条主干(把 9.1 走完)。选路焦虑的解药不是想清楚,而是把主干的每一步做实。
8. 延伸资源
- 各校研究生院官网的推免细则(当年为准)
- 一亩三分地/知乎的多模态方向申请与就业样本帖(当哨兵,不当真理)
- OpenReview + 导师主页——PhD 套磁的前期调研工具
9.3 作品集打造与个人品牌:让 GitHub 替你说话
本章目标:把你 9 个月作业里散落的产出,组装成”面试官 3 分钟能看懂、导师 30 秒能被打动”的作品集。核心命题:作品集是这个时代学生的第二简历,而且比简历诚实。学完标准:有一个可交付的作品集架构和每项目的”3 分钟讲法”。
1. 原则:少而硬,假不了
- 2–3 个”小而硬”的 repo > 10 个 toy demo(总路线的判断,这里是执行标准)——“硬”的定义:有数字结果、有失败记录、有你自己的分析(不是抄来的教程);
- 诚实是最强的差异化:面试官看惯了”基于 XXX 实现了 YYY”的模糊话术,看到”复现 LLaVA,缩放到 0.5B,消融发现 projector 学习率是主敏感项,差异表如下”的 candidate 会立刻警觉地认真起来——具体的数字+具体的失败 = 真做过的签名。
2. 一个”硬” repo 的解剖(模板)
my-repo/
├── README.md ← 决定生死的 3 分钟
├── requirements.txt ← 版本钉死(别写 torch 即了事)
├── src/ … ← 可读的代码(关键函数有注释为什么)
├── configs/ ← 实验配置(可一键复跑)
└── assets/ ← 结果图/曲线/对比案例
README 六段式(顺序即阅读优先级):
- 一句话 + 结果数字(“QLoRA 微调 Qwen2.5-7B 实现流派识别 VLM,留出集 84.2%,比底座 +11.3%”);
- 主结果图(1–2 张,曲线/对比案例拼图);
- 复现命令(3 行内跑通 demo——跑不起来的一切白搭);
- 关键发现 2–3 条(含失败:“试过解冻视觉塔,灾难性遗忘,见 analysis.md”);
- 与论文/教程的差异(你的增量在哪);
- 后续 TODO(证明项目活着)。
3. 作品集阶梯(与 9.1 计划一一对应)
| 时间点 | 交付物 | 讲法关键词 |
|---|---|---|
| W6 | nn-from-scratch(micrograd 引擎+CIFAR) | “从零手写反向传播,数值对拍验证” |
| W12 | clip-zero-shot(1.6 项目) | “prompt 集成提分 X%,检索 demo” |
| W20 | 7B 微调 + HF/魔搭模型页 | “QLoRA 显存账/失败模式三连” |
| W30 | llava-mini + 领域 VLM(8.5 配方) | “两阶段消融/三层评测” |
| 持续 | 领域项目(A1/4.6/5.1 任一) | “数据集+基准+基线” 的组合拳 |
全链一致性:这些 repo 共同讲一个故事——“从引擎到模型到评测到领域,多模态全栈都亲手摸过”。故事线比单个项目更值钱。
4. 写作资产:让项目被看见
- 每个项目一篇知乎/博客(1500–3000 字):不是教程复读,写你踩的坑与你的消融——教程千篇一律,踩坑独此一家;
- 实验台账公开化(wandb report 链接进 README)——曲线比截图可信;
- 公开精读笔记(6.1 的模板产物)——展示阅读品味,导师套磁时是绝佳附件;
- 节奏:一个月一篇,积累一年就是 12 篇——数量自然形成”个人品牌”,不用刻意运营。
5. GitHub 卫生学(低成本高回报)
- Profile README(一段话+方向标签+代表作品链接);
- Pin 3–4 个代表 repo(首页即作品集);
- commit 纪律:小步提交、有意义的 message(
fix: gradient accumulation sync under DDP)——面试官会翻; - README 里的图务必传图床/GitHub asset(挂本地路径=翻车现场)。
6. 3 分钟讲法(面试的弹药夹)
每个项目备好三个层次:
- 30 秒版:问题/做法/结果数字(电梯场合);
- 3 分钟版:+ 关键决策点(“为什么选 QLoRA 不是全参?显存账在此”)+ 一个失败与修复(最有说服力的段落);
- 追问防御:任何数字都能往下拆两层(“84.2% 怎么来的?评测协议:300 条留出、盲测基线 41%、judge 校准一致率 87%”)——6.3 的协议冻结在这里直接变现。
练习法:对着手机录音讲一遍,回听——讲不清的地方就是你没真懂的地方(和 2.10 的收官自查同一招)。
7. 自测题
- “小而硬”的三个判据?(数字结果/失败记录/自己的分析)
- README 六段的顺序原则是什么?(按面试官注意力衰减排序——数字最前)
- 为什么”失败记录”是诚实签名?(教程里没有失败——有失败说明真跑过)
- 作品集阶梯的故事线一句话?(从引擎到模型到评测到领域的多模态全栈亲手摸过)
- 3 分钟讲法的”追问防御”靠什么支撑?(6.3 的协议冻结+实验台账——细节可拆两层)
- 写作资产的复利机制?(每月一篇踩坑文→一年自然形成品牌——附属于项目而非独立运营)
8. 动手作业(本周就能做)
- 用 §2 模板重构你已有的第一个 repo(哪怕只是 0.2 的 CIFAR 脚本)——今天;
- 写你的 Profile README(10 分钟);
- 给 W6 里程碑的 repo 写 3 分钟讲法并录音自测;
- 建
portfolio-roadmap.md:把 §3 阶梯贴进去,每个交付物旁边留”3 分钟讲法”占位——按 9.1 节奏逐格填充。
9. 延伸资源
- GitHub 官方《关于 profile README》文档
- 知乎”我的保研/求职作品集”经验帖若干——当参照系,不当模板
- wandb reports——实验报告的展示形态
9.4 实习申请与面试准备:从简历到 offer
本章目标:把 9.1–9.3 的积累兑换成实习 offer——时机选择、简历写法、渠道优先级、面试四关的打法。学完标准:有一份能投出去的简历和每个项目的 3 分钟讲法,知道面试官在每个环节真正在筛什么。
1. 时机:你画像下的实习窗口
- 2027 暑假(大三下结束):第一个黄金窗口——保研铺垫(科研实习,导师组/研究院)或企业实习(大厂多模态团队)二选一;此时你按 9.1 已有 LLaVA 复现+领域项目;
- 大四上:保研成功者可选科研实习(冲论文)或提前进未来导师组;考研者不实习;就业者暑期实习转正是主线;
- 科研实习 vs 企业实习(2026 现实):研究院/高校联培(论文导向,有署名机会)vs 大厂业务组(工程导向,转正机会)——想读博选前者,想就业选后者,别贪两者兼得。
2. 简历一页法(写给 10 秒扫描的初筛官)
- 结构:教育背景(GPA/排名若亮眼)→ 实习/科研经历 → 项目经历(2–3 个)→ 技能 → 荣誉;
- 项目条目公式:动词 + 做了什么 + 数字结果(“复现 LLaVA 两阶段训练,缩放至 0.5B,构建三层评测集,阶段一消融发现 projector lr 为主敏感因素”)——每条都对应 9.3 的 repo 链接(简历放 GitHub 链接,PDF 里可点击);
- 三条纪律:不写”熟悉/了解”(写”用 X 做成了 Y”);不写没用过的技术名词(深挖环节必翻车);一页,删到一页。
3. 渠道优先级(命中率排序)
导师/师兄师姐内推 > 组里合作企业的实习转岗 > 官网 research intern 项目(字节 Seed/阿里通义/腾讯混元/快手可灵/智谱等的实习生计划)> 实习平台海投。科研实习的特殊渠道:目标论文作者的主页”Join us”栏目 + 套磁信(8.9 的三句话框架通用)。时间线:大厂暑期实习一般 3–5 月投递、5–6 月面试——大三下的 W25 前后就要开始投(9.1 计划里已埋)。
4. 面试四关的打法
关 1:简历深挖(30 分钟,决定性的一关)
面试官在验证”这是不是你做的”。打法:9.3 的三层弹药(30 秒版/3 分钟版/追问防御)+ 主动交代失败(“这个实验我们踩过 template 错位的坑”——7.2 案例集在这里变现)。筛掉的是:讲不清自己 repo 里代码的人。
关 2:编码(30–60 分钟)
算法岗标配:LeetCode 中等难度(热题 100 足够)+ ML 手写题——手写 multi-head attention、手写卷积前向、手写 NMS/IoU 是出现率最高的三道,全是本笔记 1.2/1.8 的作业原题。防线:不追求刷题量,追求”手写 attention 不看资料 10 分钟写对”。
关 3:ML/多模态基础(20 分钟)
高频题清单(本笔记自测题的原题池):LoRA 原理与 B 置零、KV cache 显存账、GQA、BN/LN 区别、mAP/IoU、attention 平方复杂度与 FlashAttention 思想、DPO vs GRPO、数据污染怎么防——每章自测题的答案就是你的面试题库。
关 4:反向提问(10 分钟,被低估的一关)
好问题示例:“实习生在组里的工作流是怎样的?mentor 制度?”、“组里最近的某篇工作里 X 设计是怎么定下来的?“——反向提问在替你筛团队,也在展示你的认真程度。
5. 实习期间的三条纪律
- 每周 sync 记录:做了什么/卡在哪/下周计划——转正答辩的素材在第一天就开始攒;
- mentor 关系:主动汇报节奏对齐 mentor 期望(大部分差评源于期望错位而非能力);
- 转正叙事:一个”从 0 到 1 归你的”交付物(哪怕很小:一个评测管线/一个数据清洗工具)胜过十件打杂。
6. 自测题
- 科研实习与企业实习的选择判据?(读博/论文 vs 就业/转正——别贪兼得)
- 简历条目公式与三条纪律?(动词+做了什么+数字;不写”熟悉”、不写没用过、一页)
- 渠道命中率排序?(内推>转岗>官方 intern 项目>海投)
- 面试四关里哪关是决定性的?筛什么?(简历深挖——验证”是不是你做的”)
- 手写题出现率最高的三道与出处?(attention/卷积/NMS——1.2/1.8 作业原题)
- 转正叙事的核心?(一个归你的从 0 到 1 交付物+每周记录攒素材)
7. 动手作业
- 写简历 v1(一页,严格按 §2),找一位同学/师兄互审;
- 把每个作品集项目录一遍 3 分钟讲法(9.3 的作业转正);
- LeetCode 热题 100 启动(每天 1 题,寒假完成);手写 attention 计时训练(目标 10 分钟闭卷);
- 建立目标清单:5 个 research intern 项目 + 5 家企业团队,各记投递窗口与内推人。
8. 延伸资源
- 目标团队官方校招/实习页(Seed/通义/可灵/混元等)——一手 JD 与窗口
- LeetCode 热题 100——编码关的全部范围
- 牛客面经(多模态算法岗)——当模拟题库,不当真理
附录 · 全书术语速查表
用法:读论文/复习/面试前快速过一遍。每条一句话定义 + 出处章节。建议用法:遮住定义,只看术语能否复述——说不出就跳回对应章节。
A. 基础与训练
| 术语 | 一句话定义 | 出处 |
|---|---|---|
| 交叉熵 / NLL | 训练目标的本体:让模型输出分布逼近真实分布;梯度 = 预测 − 标签 | 0.1 |
| KL 散度 | 两个分布的差异度量;对齐技术里的”缰绳”(别漂太远) | 0.1 / 2.7 |
| AdamW | 现代默认优化器:Adam + 解耦的权重衰减 | 0.1 |
| warmup + cosine | 学习率先升后降的标准节奏 | 0.1 / 2.4 |
| 反向传播 | 链式法则自动化在计算图上:局部导数 × 逆拓扑传播 | 0.3 |
| 数值对拍 | 用 (L(θ+ε)−L(θ−ε))/2ε 验证手写梯度——防静默错误的唯一硬手段 | 0.3 |
| RMSNorm | LayerNorm 的简化版(只除均方根);LLaMA/Qwen 系标配 | 0.3 / 2.3 |
| 残差连接 | y = x + F(x):学增量而非从头学;梯度高速公路 | 1.1 / 0.3 |
| AMP / bf16 | 混合精度:低精度算、高精度存;bf16 免 loss scale | 0.4 |
| EMA | 权重的指数滑动平均副本——震荡轨迹的平均,评测更好 | 0.4 / 1.5 |
| 单 batch 过拟合 | 调试第一定律:一个 batch 降不到 0 = 代码有 bug | 0.4 |
B. 架构与 LLM
| 术语 | 一句话定义 | 出处 |
|---|---|---|
| Attention | 按相关性加权取材:QKᵀ 打分 → softmax 归一 → 加权 V | 1.2 |
| 1/√d_k | 打分方差控制——防止 softmax 饱和 | 1.2 |
| causal mask | 上三角填 −∞:GPT 不会偷看未来 | 1.2 / 1.3 |
| Pre-Norm / 残差流 | Norm 包子层输入;残差主干是信息高速公路 | 1.3 |
| RoPE | 旋转位置编码:内积只依赖相对距离,可外推 | 1.3 / 2.3 |
| SwiGLU | 门控 MLP:down(silu(gate(x))·up(x)),现代标配 | 1.3 |
| decoder-only | GPT 范式:自回归 + 因果 mask,生成理解统一 | 1.3 / 2.1 |
| ViT / patch | 图像切 16×16 块当 token——“一切皆 token”的视觉开端 | 1.4 |
| MAE | 遮 75% 重建:视觉自监督;遮罩率跟模态冗余度走 | 1.5 |
| CLIP / InfoNCE | 图文对齐空间;batch 内配对拉近、其余推远 | 1.5 / 1.6 |
| DINO | 自蒸馏 + centering 防坍塌;注意力涌现分割;机器人底座 | 1.5 |
| BPE | 字节级贪心合并的子词切分——模型真正看到的”字” | 2.2 |
| KV cache | 缓存历史 K/V,每步只算新 token——推理省算的根基 | 2.3 |
| GQA | K/V 头分组共享——KV cache 省 4 倍的标准手法 | 2.3 / 2.8 |
| prefill / decode | 一次读整个 prompt(compute-bound)vs 逐 token 生成(memory-bound) | 2.3 / 2.8 |
| scaling law / 6ND | loss 随规模幂律下降;训练算力 ≈ 6×参数×token | 2.1 / 2.4 |
| Chinchilla 配比 | 每参数约 20 token 训练最优;LLaMA 故意”过训”换推理便宜 | 2.4 |
| SFT / loss mask | 指令微调只在回答位置算 loss(−100 掩码) | 2.5 |
| MoE | 专家路由:总参数与每 token 激活量解耦 | 2.9 |
C. 多模态
| 术语 | 一句话定义 | 出处 |
|---|---|---|
| 三条路线 | 双塔对齐 / 桥接 connector / 原生融合——融合点不断提前 | 3.1 |
| 视觉 token 是外语 | VLM 的核心心智模型:LLM 架构不变,序列里多了外来词 | 3.1 |
| AnyRes / 动态分辨率 | 高分辨率切块+缩略图;token 预算随内容变化 | 3.2 / 3.3 |
| pixel shuffle | 空间重排到通道维的无损压缩——开源 VLM 主力手法 | 3.3 |
| Q-Former 之死 | 复杂 connector 输给 MLP+好数据——“数据>架构”最强案例 | 3.3 |
| VQ-VAE / VQGAN | 图像离散化:码本量化 + 直通估计器;离散生成的地基 | 3.4 |
| tokenizer 天花板 | 重建上限 = 离散生成路线的上限 | 3.4 |
| OCR-free | 文档图端到端出结构化结果——版面语义联合建模 | 3.6 |
| 数据污染 | 评测题混进训练数据——背题不是能力;防:隔离去重+扰动测试 | 3.7 |
| 盲测基线 | 遮图重测——“有图减无图”的增量才是视觉能力 | 3.7 / 5.1 |
| LLaVA 两阶段 | 一冻 LLM 学翻译(对齐),二解冻学行为(指令微调) | 3.2 |
D. 生成模型
| 术语 | 一句话定义 | 出处 |
|---|---|---|
| 扩散 / DDPM | 前向闭式加噪 + 学”指认噪声”;噪声=数据密度的梯度方向 | 4.2 |
| DDIM / ODE 视角 | 采样=解反向轨迹方程;可跳步、可确定性 | 4.3 |
| CFG | 条件方向放大的特效药;s 过大→塑料感 | 4.3 |
| LDM / VAE-f8 | 先压缩 48 倍再扩散——潜空间画布 | 4.4 |
| cross-attention 注入 | 文生图条件机制本体:图像 Q 查文本 K/V | 4.4 |
| DiT / adaLN-Zero | 生成模型 Transformer 化;条件调制 norm,gate 零初始化 | 4.5 |
| Flow Matching / RF | 直线插值学速度场:无 schedule、路径直、采样省步 | 4.5 |
| spacetime patch | 视频=3D token——“一切皆 token”的时空推广 | 4.7 |
| 统一模型三路线 | 全离散(Chameleon) / 混合损失(Transfusion) / 解耦编码(Janus) | 4.8 |
| 扩散语言模型 | 掩码并行去噪替代自回归——双向上下文+高吞吐 | 4.9 |
E. 对齐与前沿
| 术语 | 一句话定义 | 出处 |
|---|---|---|
| RLHF / KL 惩罚 | 奖励模型打分 + 别漂太远的缰绳 | 2.7 |
| DPO | 偏好直接监督化:奖励被闭式解消掉 | 2.7 |
| GRPO / RLVR | 组内相对优势省掉 critic;可验证奖励是当代推理引擎 | 2.7 / 5.1 |
| reward hacking | 钻奖励空子(格式猜答案/遮图不掉分)——验证器设计的永课题 | 5.1 / 8.6 |
| thinking with images | 裁剪/放大/检索作为推理动作——主动取证 | 5.1 / 8.5 |
| VLA | VLM 输出动作 token/连续轨迹——具身的接口 | 5.3 |
| 世界模型 | 状态+动作→下一状态的内部模拟器;JEPA 主张只在表征空间预测 | 5.4 |
| GUI Agent | 截图→grounding→动作→校验;瓶颈在长时程误差累积 | 5.6 |
| 3DGS / 前馈重建 | 显式高斯实时渲染;VGGT=3D 的 SAM 时刻 | 5.5 |
| 蒸馏 / 数据蒸馏 | 大教小:logit 对齐 → 大模型造数据训小模型 | 5.8 |
F. 工程与科研
| 术语 | 一句话定义 | 出处 |
|---|---|---|
| 显存 16B/参数 | 全参混合精度的账:权重2+梯度2+AdamW 8+主权重4 | 7.1 |
| OOM 决策树 | 先测量→降 batch→checkpoint→查 no_grad→降序列→分布式 | 7.1 |
| 数据版本化 | 数据当代码管:来源哈希+管线版本+统计+评测锁 | 7.5 |
| 可复现五要素 | checkpoint 要带 opt/sched/epoch/rng/配置 | 0.4 |
| 最小复现七步法 | 提取主张→缩放→对照→差异表——复现的是主张不是代码 | 6.2 |
| 协议冻结 | 评测规则实验前写死——防”事后调协议凑分” | 3.7 |
| 三遍读论文 | 分诊/通读/精读,10%/30%/10% 的取舍纪律 | 6.1 |
| 一页 proposal | 问题假设/实验矩阵/算力三行/风险降级——立项标准格式 | 6.3 |
| 图先行写作 | 先固化图表再写正文——叙事跟着结果走 | 6.4 |
| 零初始化哲学 | 新模块从恒等出发不破坏预训练:LoRA-B/Flamingo 门控/adaLN/zero-conv 四连 | 2.6/3.3/4.5/4.6 |
74 章正文里所有加粗术语都在本章的延长线上——发现漏网高频词,说一声即补。
中英对照速览(读论文/写论文双向查)
| 中文 | English | 中文 | English |
|---|---|---|---|
| 交叉熵 | cross-entropy | 负对数似然 | negative log-likelihood (NLL) |
| 困惑度 | perplexity | 温度 | temperature |
| 反向传播 | backpropagation | 数值梯度 | numerical gradient |
| 残差连接 | residual/skip connection | 归纳偏置 | inductive bias |
| 混合精度 | mixed precision (AMP) | 梯度累积 | gradient accumulation |
| 断点续训 | resume from checkpoint | 指数滑动平均 | EMA |
| 注意力机制 | attention mechanism | 多头 | multi-head |
| 因果掩码 | causal mask | 位置编码 | positional encoding |
| 旋转位置编码 | RoPE | 查询/键/值 | query / key / value |
| 前馈网络 | feed-forward network (FFN) | 门控 | gated (SwiGLU) |
| 图像块 | patch | 视觉 token | visual token |
| 自监督 | self-supervised | 对比学习 | contrastive learning |
| 图文对齐 | image-text alignment | 零样本 | zero-shot |
| 提示词工程 | prompt engineering | 模板 | chat template |
| 分词器 | tokenizer | 子词 | subword |
| 键值缓存 | KV cache | 并发/吞吐/延迟 | concurrency / throughput / latency |
| 量化 | quantization | 投机解码 | speculative decoding |
| 指令微调 | instruction tuning (SFT) | 灾难性遗忘 | catastrophic forgetting |
| 低秩适配 | LoRA (low-rank adaptation) | 合并权重 | merge weights |
| 人类反馈强化学习 | RLHF | 直接偏好优化 | DPO |
| 可验证奖励 | verifiable reward (RLVR) | 组相对策略优化 | GRPO |
| 奖励作弊 | reward hacking | 拒绝采样 | rejection sampling |
| 提示注入 | prompt injection | 幻觉 | hallucination |
| 数据污染 | (benchmark) contamination | 去重 | deduplication |
| 消融实验 | ablation study | 基线 | baseline |
| 掩码建模 | masked modeling | 直通估计器 | straight-through estimator |
| 码本 | codebook | 码本坍塌 | codebook collapse |
| 潜空间 | latent space | 噪声调度 | noise schedule |
| 引导系数 | guidance scale | 负面提示词 | negative prompt |
| 扩散/流匹配 | diffusion / flow matching | 时间步 | (diffusion) timestep |
| 视觉语言模型 | VLM | 多模态 | multimodal |
| 指代表达/指框 | referring expression / grounding | 光学字符识别 | OCR |
| 显著性 | saliency | 负空间 | negative space |
| 明暗对比 | chiaroscuro | 笔触 | brushstroke |
| 图像学 | iconography | 流传有序 | provenance |
附录 · 十卷思维导图
用法:每卷开卷前看一眼(知道地图),合卷后再看一眼(自测回忆——遮住子节点,看能展开多少)。Mermaid mindmap 渲染,节点即章节关键词。
卷0 · 基础篇
mindmap
root((卷0 基础篇))
数学
内积=相似度
交叉熵=训练目标
KL=缰绳
AdamW与lr节奏
6ND算力账
PyTorch
张量与广播
训练循环
显存速算与OOM三板斧
反向传播
计算图与链式法则
手写micrograd
数值对拍
RMSNorm
训练工程
AMP与bf16
断点续训五要素
单batch定律
EMA与梯度裁剪
远程开发
Git铁律
tmux保命
租卡流程模板卷1 · 深度学习与CV
mindmap
root((卷1 现代CV))
CNN到ResNet
卷积四视角
残差=学增量
归纳偏置与数据规模
注意力
QKV与1比根d
causal mask
FlashAttention思想
Transformer
Pre-Norm残差流
RoPE与SwiGLU
手写TinyGPT
参数量12d2
ViT与谱系
patch化=16x16卷积
Swin与ConvNeXt
token数量矛盾
自监督
MAE遮75
CLIP对齐
DINO自蒸馏
CLIP实操
zero-shot
prompt集成
检索demo
SAM
三件套
提示范式
数据引擎自举
检测分割史
四幕剧
U-Net双血统
相机模型
针孔投影
内外参
COLMAP四步卷2 · LLM 内功
mindmap
root((卷2 LLM内功))
前史
ngram死穴
word2vec
GPT三张牌
BPE
贪心合并
字节兜底
数字切分翻案
GPT工程版
升级清单
KV cache账
GQA
prefill与decode
预训练
数据管线四步
Chinchilla与过训
6ND
spike处置
SFT
loss mask
模板错位
LIMA
LoRA
低秩与B置零
rank选择
QLoRA三件套
merge与adapter
对齐
RLHF三步
DPO闭式
GRPO组内优势
RLVR
推理
量化三路
PagedAttention
投机解码
成本账
前沿与小模型
MoE
长上下文
甜点区选题卷3 · 多模态理解
mindmap
root((卷3 VLM))
三条路线
双塔对齐
桥接connector
原生融合
四问清单
LLaVA
两阶段
inputs_embeds
失败模式表
Connector
Resampler
Q-Former之死
pixel shuffle
动态分辨率
视觉tokenizer
VQVAE
码本坍塌
天花板定律
双雄精读
Qwen演化
InternVL演化
选底座决策
文档理解
OCR-free
MinerU管线
评测
五大陷阱
协议冻结
盲测基线
数据案例
665K构成
配比读表法卷4 · 生成模型
mindmap
root((卷4 生成))
五大家族
AR
VAE
GAN
扩散
Flow
DDPM
闭式加噪
指认噪声
MNIST实现
采样与CFG
ODE视角
DDIM跳步
guidance scale
SD
三大件
潜空间48倍
换代逻辑
DiT与Flow
adaLN-Zero
直线速度场
MMDiT
可控生成
ControlNet
IP-Adapter
风格LoRA
zero-conv
视频
时空token
开源阵营
世界模型合流
统一模型
Chameleon
Transfusion
Janus解耦
扩散LM
掩码并行
与AR对比卷5 · 前沿专题
mindmap
root((卷5 前沿))
推理RL
三条路线
学生GRPO配方
reward hacking
数据为中心
四类数据
五指标体检
固定模型动数据
具身VLA
离散与连续动作
sim2real
LIBERO路线
世界模型
四种形态
JEPA主张
物理探针
3D
NeRF
3DGS
VGGT前馈
Agent
五层栈
SoM提示
误差累积
医学与科学
三特殊性
nnUNet与MedSAM
合规三件套
高效化
五杠杆
蒸馏三阶段
端侧三件套卷6 · 科研方法论
mindmap
root((卷6 方法论))
读论文
三遍法
藏猫腻清单
精读模板
复现
七步法
三层归因
timebox
选题
四条标准
文献扫描五步
一页proposal
风险降级
写作投稿
图先行
rebuttal
五条拒稿理由
开源
贡献阶梯
itch-driven
30天首PR
诚信
红绿灯表
幻觉引用防线
署名规范卷7 · 工程手册
mindmap
root((卷7 工程))
显存
16B每参数
KV账
决策树
调试案例
十大翻车
现象归因
分布式
DDP检查单
ZeRO三级
决策树
部署
单位成本
利用率修正
压测拐点
数据管线
EXIF陷阱
两层去重
版本化五要素
AI协作
分工总表
五步工作流
四大暗坑
无AI日卷8 · 美术学交叉
mindmap
root((卷8 美术学))
美术基础
三层框架
色彩构图光影
概念可计算表
计算美学
NIMA分布预测
偏好奖励模型
SRCC
风格史
Gram矩阵
AdaIN统计矩
生成分布
艺术生成
artist study六步
水墨三难点
美术质检表
看画VLM
五层任务
微调RAG矩阵
看画agent
评价与对齐
偏好数据
扩散DPO
奖励钻空子
数据集
标注规范五节
kappa三把尺
版权红线
文化遗产
编目管线
数字人文远读
修复伦理
选题库
二十题
决策树
A1为底座卷9 · 生涯执行
mindmap
root((卷9 生涯))
周计划
五阶段
夏令营清单
导师模板
四条路
保研最优
考研复试变现
PhD硬通货
就业项目优先
决策截止2027.6
作品集
小而硬三判据
README六段
三分钟讲法
面试
四关打法
手写题三道
反向提问附录 · 论文精读包(10 篇核心论文预读笔记)
定位与诚实声明:这是按 6.1 模板写的预读笔记(第二遍通读水平的产物),作用是给你”读前地图”——不能替代你的第三遍精读,且细节以原文为准(AI 预读可能有偏差,发现对不上就回原文)。建议用法:读到对应章 → 先看这里的地图 → 带着地图读原文 → 补自己的第三遍笔记。 顺序按学习路径排列,与正文章节互相链接。
1. Attention Is All You Need (2017) · NeurIPS
- 出处:arXiv 1706.03762|对应:1.2/1.3|arXiv 页见资源索引
- 问题与主张:序列转换(翻译)依赖 RNN 的串行计算;主张完全用注意力替代循环——并行训练 + 一步直达的长程依赖。
- 方法一页:Encoder-Decoder 各 N=6 层;多头自注意力(h=8, d_k=64)+ 位置正弦编码 + FFN;decoder causal mask;bpe 3.7 万词表。
- 关键证据:WMT14 英德 28.4 BLEU,超一切先前模型且训练成本只要其零头(3.5 天 × 8 P100)。
- 可复现性:tensor2tensor 开源;现代复现用 nanoGPT 更简单。
- 与你的课题:一切的原点;面试必考多头动机与 mask。
- 一句话:把”序列建模”改写成”集合上的可微查字典”,此后一切架构争论都在它的延长线上。
2. An Image is Worth 16x16 Words — ViT (2020) · ICLR
- 出处:arXiv 2010.11929|对应:1.4
- 问题与主张:CNN 的视觉先验是否必需?主张:纯 Transformer + patch 化,在足够数据下反超。
- 方法一页:16×16 patch → 线性投影(等价 k16/s16 卷积)+ CLS token + 可学习位置编码 → 标准 encoder;微调接线性头。
- 关键证据: scaling 曲线——JFT-300M 预训练后 ImageNet 88%+;小数据输 ResNet(诚实的负结果也在论文里)。
- 可复现性:timm 一行加载;论文消融清晰可重算。
- 与你的课题:1.4 作业的对照对象;“数据换先验”曲线是你理解一切视觉基础模型的钥匙。
- 一句话:图像成为 token 的出生证明。
3. Learning Transferable Visual Models — CLIP (2021)
- 出处:arXiv 2103.00020|对应:1.5/1.6/8.2
- 问题与主张:视觉模型困在固定类别;主张用 4 亿网络图文对做对比学习,获得可迁移的零样本能力。
- 方法一页:双塔(ViT + 文本 Transformer)→ L2 归一化 → 对称 InfoNCE(batch 32768、可学习温度 0.07);zero-shot = 类名 prompt 检索。
- 关键证据:zero-shot ImageNet 76.2%(prompt 集成后),追平有监督 ResNet-50;表征迁移全面强于 ImageNet 监督特征。
- 可复现性:open_clip 全系复现;WIT 数据未开源(复现用 LAION)。
- 与你的课题:你的第一个项目(1.6);美学评分(8.2)、数据过滤、奖励模型全站在它肩上。
- 一句话:自然语言监督把视觉从”分类器”解放成”对齐空间”。
4. MAE (2021)
- 出处:arXiv 2111.06377|对应:1.5
- 问题与主张:BERT 式掩码预训练在视觉为什么之前不行?主张:高遮罩率(75%)+ 非对称设计。
- 方法一页:编码器只见可见 patch(省 3 倍算力)→ 轻量解码器带 mask token 重建像素 → MSE 只在遮罩位。
- 关键证据:75% 最优(遮少了不用动脑);ViT-H 迁移全面涨;视觉与语言的预训练效率差距被抹平。
- 可复现性:官方代码极简;一天单卡复现小规模。
- 与你的课题:理解”遮罩重建”这条线——它通向 3.4 的离散 tokenizer 与 4.x 生成思想。
- 一句话:视觉的完形填空,简单到让人怀疑的里程碑。
5. LLaVA-1.5 (2023)
- 出处:arXiv 2310.03744|对应:3.2(本章就是它的精读扩充版)
- 问题与主张:多模态指令跟随需要复杂架构吗?主张:CLIP 视觉塔 + 两层 MLP + 好数据就够。
- 方法一页:两阶段(caption 对齐 projector → 学术任务数据全参微调);MLP 投影、336px、665K 指令数据。
- 关键证据:全面超越 InstructBLIP(Q-Former 系)——同规模下”简单架构+好数据”赢。
- 可复现性:官方 repo 开源;你的迷你复现(3.2 作业)就是它的缩放版。
- 与你的课题:你大三下的主线项目;它的 ablation 表是”数据>架构”的第一手证据。
- 一句话:VLM 的”简单基线宣言”——复杂度应该花在数据上。
6. Qwen2-VL (2024)
- 出处:arXiv 2409.12191|对应:3.5
- 问题与主张:固定分辨率浪费预算且丢细节;主张 NaViT 式动态分辨率 + M-RoPE。
- 方法一页:原生比例切 patch(token 数随内容变)、时间/高/宽三维解耦的位置编码、agent/grounding 后训练强化。
- 关键证据:DocVQA/数学/grounding 多域 SOTA;小时级视频理解。
- 可复现性:权重开放(2B–72B);LLaMA-Factory 全支持——学生甜点区首选底座。
- 与你的课题:8.9 选题的默认底座;它的报告是”配置清单读表法”(3.5 §2)的标准练习材料。
- 一句话:动态分辨率+三维位置编码——当代 VLM 的公共底盘由它定型。
7. LoRA (2021)
- 出处:arXiv 2106.09685|对应:2.6
- 问题与主张:微调大模型的适配器们(Adapter/Prefix)有推理开销;主张:权重变化低秩,旁路 BA 即可,部署零开销。
- 方法一页:ΔW=BA(r≪d),A 高斯 B 置零,缩放 α/r,只训旁路;可合回 W。
- 关键证据:GPT-3 175B 上 r=4 即匹配全参微调;参数量万分之一。
- 可复现性:peft 标准化;你 2.6 的手写实现就是对它的复现。
- 与你的课题:你未来两年用得最多的技术;“低秩假设”直接连 0.1 的 SVD。
- 一句话:低秩假设的工程胜利——微小参数预算撬动全部适配能力。
8. DPO (2023)
- 出处:arXiv 2305.18290|对应:2.7
- 问题与主张:RLHF 的 PPO 循环复杂且不稳;主张:偏好目标有闭式解,奖励模型可以整个消掉。
- 方法一页:最优策略下 r = β·log(π_θ/π_ref) 代回 Bradley-Terry → 直接对成对偏好做监督式 loss。
- 关键证据:与 PPO 版 RLHF 在偏好胜率上相当,实现与调参成本低一个量级。
- 可复现性:TRL
DPOTrainer一小时上手;2.7 作业做过数值案例。 - 与你的课题:8.6 的扩散 DPO 是它的图像版——一套思想吃两个域。
- 一句话:把”强化学习问题”化简成”监督学习问题”的漂亮代数。
9. DDPM (2020)
- 出处:arXiv 2006.11239|对应:4.2
- 问题与主张:扩散模型此前质量不佳;主张:预测噪声的简化目标 + 大模型 + 精调 schedule,首次超越 GAN 的 FID。
- 方法一页:前向闭式加噪 → 网络 ε_θ 预测噪声(ELBO 简化)→ ancestral 采样 1000 步;线性 β、EMA、自注意力于低分辨率层。
- 关键证据:CIFAR-10 FID 3.17(当时最优);消融证明”预测 ε 的简化 loss”与完整 ELBO 质量相当且稳定。
- 可复现性:你 4.2 的 MNIST 迷你版 + Annotated Diffusion——单卡周末级。
- 与你的课题:一切生成模型的地基;“去噪=学 score”的直觉在 8.6(对齐副作用)还要回来。
- 一句话:把”生成”重新定义为”迭代的去噪”——稳定、多样、可规模化。
10. DeepSeek-R1 (2025)
- 出处:arXiv 2501.12948|对应:2.7/5.1
- 问题与主张:推理能力能否用 RL 直接”练”出来而非蒸馏?主张:GRPO + 可验证奖励(RLVR),纯 RL 也能长出长链推理(R1-Zero),加冷启动数据得到更可读的 R1。
- 方法一页:GRPO 组采样(去 critic)+ 规则奖励(答案正确性/格式)+ 多阶段(冷启动 SFT → 推理 RL → 拒绝采样再 SFT → 全场景 RL);蒸馏版证明小模型吃推理数据成长极快。
- 关键证据:R1-Zero 的 aha moment(回答长度自发增长);AIME 2024 上蒸馏 7B 追平 GPT-4o 级。
- 可复现性:EasyR1/verl/TRL 复现众多;你的 5.1 学生配方(3B+LoRA+GSM8K)就是它的等比缩放。
- 与你的课题:5.1 全章的源头;多模态验证器设计是你最可能的切入题。
- 一句话:证明”推理是练出来的不是蒸出来的”——把 2025 年的研究潮头对准了可验证奖励。
Anki 记忆卡组使用说明
三个 TSV 文件,双击导入 Anki(或 Anki → 文件 → 导入):
| 文件 | 卡数 | 内容 |
|---|---|---|
01-术语卡.tsv | 60 | 全书核心术语:正面=术语,背面=一句话定义+出处章节 |
02-自测题精选.tsv | 24 | 跨卷精选高频自测题(含数字账与决策类) |
导入设置:分隔符选”Tab”;字段映射:第 1 列 → 正面,第 2 列 → 背面;牌组随意(建议建一个”多模态学习笔记”父牌组)。文件首行的 #separator:tab 注释新版 Anki 会自动识别。
建议节奏:每天 20 张新卡 + 到期复习;答不上来的卡片背面都写了出处章节,回炉对应章即可。