任务定义与数据工程
在训练前定义可测量目标,建立数据来源、清洗、切分、模板和泄漏审计的完整证据链。
- 建议时长
- 7–10 小时
- 难度
- 工程进阶
- 课程位置
- 5 / 12
学完这一课,你应该能:
- 能把模糊需求改写成可评测任务
- 能设计避免同源泄漏的数据切分
- 能审计指令数据的模板、长度和标签
- 能产出可重建的数据卡与黄金测试集
1. 训练前先写“成功是什么”
“让模型更懂公司知识”不可直接训练,也不可验收。先拆成:
输入分布:内部技术问题,中文,平均 220 tokens
期望行为:给出步骤、引用依据、不编造不存在的接口
硬约束:敏感字段不得输出,响应小于 3 秒
质量指标:黄金集正确率、引用覆盖率、事实错误率
系统指标:TTFT、TPOT、显存、单位请求成本
建立不微调 baseline:原模型 + 明确 prompt、原模型 + RAG。没有 baseline,就无法证明微调增益值得数据与部署复杂度。
2. Prompt、RAG、PEFT 还是全参
| 问题类型 | 首选 | 原因 |
|---|---|---|
| 少量格式约束 | Prompt | 成本最低、迭代最快 |
| 频繁变化的事实 | RAG | 更新知识无需改权重 |
| 稳定风格、流程、领域行为 | PEFT | 少量参数适配行为 |
| 大规模能力迁移且资源充足 | Full FT | 容量最大,风险成本也最高 |
若失败来自检索不到文档,LoRA 不会自动修好检索;若失败来自格式不稳定,先优化模板与约束解码。
3. 数据卡不是形式文档
name: internal-support-v3
source: approved tickets + manuals
license: internal-approved
revision: sha256:...
filters:
- remove_sensitive_fields
- exact_dedup
- semantic_dedup@0.94
split_strategy: group_by_document_and_customer
counts: {train: 8200, validation: 900, test: 1000}
known_risks:
- historical answers may contain retired APIs
数据卡的目标是让下一次实验能重建同一批数据,而不是笼统声称“高质量”。
4. 为什么随机逐行切分会虚高
工单、FAQ、长文切片常高度相似。若同一原文的片段分别进入 train 与 test,模型可能记住表达,验证分数却看似优秀。切分单位应根据业务选择:
- 用户或租户
- 文档 id / 会话 id
- 时间窗口
- 语义聚类
- 业务实体
先按组切分,再在组内处理样本。对时效任务,用过去训练、未来测试,比随机切分更接近生产。
5. 去重需要三个层级
- Exact duplicate:规范化空白、大小写、标点后做 hash。
- Near duplicate:token shingles + MinHash,或句向量相似度。
- Semantic leakage:字面不同但共享答案或源文档,按来源 id、实体或聚类检查。
from collections import defaultdict
split_by_source = defaultdict(set)
for row in rows:
split_by_source[row["source_document_id"]].add(row["split"])
leaked = {
source: splits
for source, splits in split_by_source.items()
if len(splits) > 1
}
print("cross-split sources:", len(leaked))
相似度阈值不是固定真理。必须人工抽样误删与漏删,说明为什么选择 0.92 或 0.95。
6. 指令数据到底监督什么
对 chat 数据,常见目标是只计算 assistant token 的 loss:
system tokens labels = -100
user tokens labels = -100
assistant tokens labels = token ids
padding tokens labels = -100
若把 user prompt 也作为标签,模型会花容量学习复述输入;若把所有 token 都设为 -100,没有有效监督。必须统计:
- assistant 有效监督 token 数
- 被截断答案比例
- prompt/answer 长度分布
- 空答案、重复答案、角色缺失
- 模板 token 分布
7. Packing 与截断
Packing 把多条短样本拼到固定长度序列,提高 token 利用率,但要明确:
- 不同样本是否能互相 attention
- position ids 是否重置
- label mask 是否跨边界
- EOS 是否正确插入
截断应先问“保留问题还是答案”。监督微调中,切掉答案通常更严重。记录截断率,人工检查最长的 50 条。
8. 黄金集与错误分类
黄金集应冻结并覆盖:高频正常、长尾边界、拒答安全、易混淆概念、时效性与不存在信息。建立失败 taxonomy:
retrieval_miss
instruction_not_followed
fact_hallucination
incomplete_reasoning
format_error
safety_violation
单一总分无法告诉你该改数据、检索、训练还是解码。错误类别的变化比平均分更有决策价值。
9. 本课实验:制造一次泄漏
在 GLUE 子任务或自建小数据上:
- 复制或轻改 10% 样本,让近重复跨 train/test。
- 比较随机逐行切分与按语义组切分。
- 训练同一 baseline,记录指标差。
- 用 exact、MinHash 或 embedding 方法检测。
- 人工抽样 50 对,估算检测准确性。
交付 data-card.md、leakage-audit.csv、切分脚本和结论。GLUE 适合训练评测流程练习,但性能已高度饱和,不应把其分数当现代生成模型的完整能力代表。
10. 练习与答案提示
- 同一客户多个工单能随机跨 split 吗?**答:**通常不应,容易泄漏特有表达。
- 为什么测试集不能反复调参?**答:**测试反馈会变成隐含训练信号。
- RAG 知识更新为何通常无需微调?**答:**事实存于可更新外部语料。
- Packing 一定提高效果吗?**答:**主要提高利用率;边界错误会伤害训练。
- 数据 hash 能证明质量吗?**答:**只能证明版本一致,不能证明内容正确。