为什么需要 Few-shot Prompting
我们已经讲过 CoT(推理)、ToT(搜索)、Step-back(抽象)、Prompt Chaining(流水线)。它们解决的是"怎么想得更深、做得更稳",但有一个共同前提:
模型得先理解你要它干什么、输出什么格式。
当你用 Zero-shot(只给指令不给示例)时,模型经常出现:
- 格式跑偏:你要 JSON,它给 Markdown
- 语气不对:你要正式,它给口语
- 边界模糊:你要 3 条,它给 5 条
- 风格漂移:你要简洁,它给长篇大论
Few-shot 的解法很简单:别讲规则,给例子。模型从 2-3 个示例中归纳模式,比读 500 字指令更准。
Few-shot vs Zero-shot vs Fine-tuning
| 维度 | Zero-shot | Few-shot | Fine-tuning |
|---|---|---|---|
| 提供示例 | ❌ | ✅ 2-5 个 | ✅ 500+ 条 |
| 改变参数 | ❌ | ❌ | ✅ |
| 上下文消耗 | 低 | 中 | 无 |
| 适配速度 | 即时 | 即时 | 需训练 |
| 格式控制 | 弱 | 强 | 最强 |
| 风格学习 | 弱 | 中 | 强 |
| 成本 | 最低 | 低 | 中-高 |
| 适合任务 | 通用任务 | 格式特殊、边界清晰 | 领域专精、大规模 |
关键边界:Few-shot 是 In-context Learning(上下文学习),不改变模型参数,适合"格式/风格/边界"适配;Fine-tuning 改变参数,适合"领域知识/深度能力"提升。
示例设计四原则
原则 1:示例要"代表性"而非"数量"
❌ 给 10 个相似的简单示例
✅ 给 3 个覆盖不同情况的示例(简单 / 边界 / 异常)
研究表明,3 个高质量示例的效果通常优于 10 个低质量示例。
原则 2:示例覆盖输出多样性
✅ 示例 1:正向案例 → 输出 A
示例 2:反向案例 → 输出 B
示例 3:边界案例 → 输出 C
❌ 示例 1:正向案例 → 输出 A
示例 2:正向案例 → 输出 A
示例 3:正向案例 → 输出 A
如果所有示例输出都一样,模型会"复制"而非"归纳"。
原则 3:示例格式与期望输出完全一致
❌ 示例输出:{"sentiment": "正面", "score": 0.9}
期望输出:{"sentiment":"正面","score":0.9}(无空格)
✅ 示例输出与期望输出格式逐字符一致
模型会模仿示例的空格、标点、换行等细节。
原则 4:示例顺序影响结果
✅ 简单 → 复杂 → 边界(递进)
❌ 边界 → 简单 → 复杂(混乱)
近因效应使最后的示例影响最大,把最接近实际任务的示例放最后。
三种示例编排模式
模式 1:标准 Few-shot(输入-输出对)
最常见,适合分类、抽取、转换任务:
任务:情感分类
输入:这家店服务态度真好,下次还来!
输出:正面
输入:质量太差了,用了一周就坏了。
输出:负面
输入:包装还行,物流一般。
输出:中性
输入:{your_input}
输出:
模式 2:CoT Few-shot(带推理的示例)
适合需要推理的任务,让模型学会"怎么想":
任务:数学应用题
问题:小明有 5 个苹果,吃了 2 个,又买了 3 个,现在有几个?
推理:5 - 2 = 3,3 + 3 = 6
答案:6
问题:一辆车时速 60km,行驶 2.5 小时,走了多远?
推理:60 × 2.5 = 150
答案:150km
问题:{your_question}
推理:
答案:
模式 3:对比 Few-shot(正反示例)
适合风格/质量把控任务,让模型学会"什么好什么不好":
任务:把口语改为书面语
✅ 好的改写
输入:这个事儿我觉得吧,咱们得赶紧弄
输出:建议尽快推进此事
❌ 不好的改写(过于生硬)
输入:这个事儿我觉得吧,咱们得赶紧弄
输出:立即执行
输入:{your_input}
输出:
实战示例:用 Few-shot 做结构化信息抽取
任务:从简历文本中抽取结构化信息
任务:从简历中抽取关键信息,输出 JSON
示例 1
输入:张三,5年Java开发经验,擅长Spring Cloud微服务,前阿里P6
输出:{"name":"张三","years":5,"stack":["Java","Spring Cloud"],"level":"P6","company":"阿里"}
示例 2
输入:李四,3年前端,React/Vue双栈,字节跳动2-1
输出:{"name":"李四","years":3,"stack":["React","Vue"],"level":"2-1","company":"字节跳动"}
示例 3(边界:信息缺失)
输入:王五,擅长Python数据分析
输出:{"name":"王五","years":null,"stack":["Python"],"level":null,"company":null}
输入:{resume_text}
输出:
对比 Zero-shot:若只给指令"抽取姓名、年限、技术栈、职级、公司",模型经常漏字段或编造。Few-shot 通过示例 3 明确了"缺失填 null"的规则。
Few-shot 与其他 Prompt 技巧的叠加
| 组合 | 效果 | 适用场景 |
|---|---|---|
| Few-shot + CoT | 示例带推理过程 | 数学、逻辑 |
| Few-shot + Step-back | 先抽象再给示例 | 复杂领域 |
| Few-shot + Chaining | 某步用 Few-shot 保证格式 | 流水线 |
| Few-shot + Self-Consistency | 多次采样取多数 | 高准确率要求 |
常见误区
- 误区 1:示例越多越好。超过 5 个示例收益递减,且消耗上下文。2-3 个最佳。
- 误区 2:示例与任务不匹配。示例的输入分布要与实际输入一致,否则模型学偏。
- 误区 3:示例输出有错误。模型会"忠实"地学会错误,示例必须人工校验。
- 误区 4:用 Few-shot 教知识。Few-shot 教的是"格式/模式",不是"事实"。事实用 RAG。
- 误区 5:示例顺序随意。最后一条示例影响最大,放最接近实际任务的。
- 误区 6:忽略示例的"负面示范"。有时给一个"不要这样做"的反例比给 3 个正例更有效。
进阶技巧
- 动态示例选择:根据输入语义检索最相似的 3 个示例(用 Embedding),效果优于固定示例
- 示例去偏:确保示例覆盖各类输出(如分类任务各类别都有示例),避免模型偏向某类
- 示例压缩:用简短示例节省 token,如
in: ... → out: ...而非完整段落 - 元 Prompt:让模型先"看完示例总结规则",再处理输入,适合复杂模式
- K-shot 标准:学术上 K 代表示例数量,Few-shot 通常指 K=1-5,K>5 收益递减
Zero-shot 何时仍是最优
不要无脑用 Few-shot,以下场景 Zero-shot 更好:
- 通用任务:翻译、摘要、改写——模型已充分训练,无需示例
- 上下文紧张:输入已接近窗口上限,示例会挤占空间
- 任务简单:单标签分类、是非判断——指令已足够
- 追求多样性:示例会限制模型创造力,创意任务少给示例
小结
Few-shot Prompting 是用示例代替规则的艺术:2-3 个精心设计的示例,能让模型秒懂新任务的格式、边界与风格,无需任何训练。当你发现 Zero-shot 跑偏、Fine-tuning 太重时,Few-shot 就是性价比最高的中间方案。
本系列下一篇将进入 自洽性(Self-Consistency),看如何通过多次采样投票进一步提升准确率。