提示工程这件事,很多人以为就是"把话说清楚",但真上手做 AI Agent 项目之后你会发现,同样一个模型、同样一个任务,提示词写得对不对,输出质量能差出三倍以上。我在搭建第一个 Agent 工作流的时候,花了整整两天调一个意图识别环节,最后发现问题根本不在代码逻辑,而是提示词里少了一句约束条件。从那以后我就养成了一个习惯:任何 Agent 项目,提示词必须当作核心代码来管理,而不是随手写一段话丢进去。
这篇内容围绕 AI Agent 学习之路的第二站——提示词与提示工程展开。不管你是刚接触大模型应用开发的新手,还是已经能跑通简单 Agent 流程但效果不稳定的开发者,这里面的思路和实操细节都能直接拿去用。我会从提示词为什么在大模型里"管用"讲起,一路拆到结构化提示词的设计方法、Agent 场景下的特殊技巧、常见翻车案例的排查链路,以及怎么把提示词当成工程资产来维护。
1. 提示词为什么能"指挥"大模型
1.1 从补全机制理解提示词的本质
要搞明白提示词为什么有效,得先理解大模型到底在做什么。本质上,大语言模型是一个"下一个 token 预测器"——你给它一段文本,它根据训练时学到的统计规律,预测接下来最可能出现的 token 序列。这个机制听起来简单,但它意味着一个关键事实:你输入的每一个字,都在改变模型对"接下来该输出什么"的概率分布。
打个比方,模型像是一个阅遍了海量文本的"超级模仿者"。你给它一个开头,它会顺着这个开头的风格、语气、逻辑往下接。你写"请用三句话总结以下内容",它就进入"总结模式";你写"你是一位资深律师,请分析以下合同条款的风险点",它就切换到"法律分析模式"。提示词的作用,就是通过精心构造的输入文本,把模型引导到你需要的那种输出分布上。
这也解释了为什么同一个问题换个问法,答案质量天差地别。不是模型"听懂"了,而是你的提示词改变了它预测下一个 token 的概率分布,让它更可能生成你想要的输出。
1.2 上下文窗口:提示词的物理边界
每个大模型都有上下文窗口限制,也就是一次能处理的 token 总量。这个窗口里要装下你的系统提示词、用户输入、历史对话、工具调用结果,以及模型即将生成的输出。很多人写提示词时忽略了这个约束,系统提示词写了三千字,用户再输入一大段,历史对话又堆了一堆,结果模型能用来"思考"的空间被严重压缩,输出质量断崖式下降。
我在实际项目里的经验是:系统提示词控制在 500 到 1500 字之间比较合理,核心指令放前面,示例和边界情况放后面。如果确实需要大量规则,考虑拆分成多个 Agent 节点,每个节点只负责一小块任务,而不是把所有规则塞进一个提示词里。
注意:不同模型的 token 计算方式不同。中文大致是 1 个汉字对应 1 到 2 个 token,英文大致是 1 个单词对应 1 到 1.5 个 token。写提示词时心里要有个大概的数,别等到报错了才想起来查。
1.3 温度参数与提示词的配合关系
温度参数控制模型输出的随机性。温度越低,输出越确定、越保守;温度越高,输出越发散、越有创造性。这个参数和提示词是配合使用的,不是独立的。
做 Agent 里的意图分类、信息抽取、格式转换这类任务时,温度建议设到 0 到 0.3,同时提示词里要给出明确的输出格式约束。做创意文案、头脑风暴这类任务时,温度可以调到 0.7 到 1.0,提示词里则要鼓励模型"给出多种可能性"。
我见过不少人调了半天提示词效果不好,最后发现是温度设成了默认的 0.7 去跑结构化抽取任务。这种问题不是提示词能救的,参数和提示词必须一起调。
2. 结构化提示词的四个核心组件
2.1 角色设定:给模型一个"身份锚点"
角色设定是提示词里最容易被低估的部分。很多人觉得"你是一个助手"这种话是废话,但实际上,角色设定给模型提供了一个"身份锚点",让它知道该从哪个知识领域、哪种语气、哪个专业水平来回答问题。
有效的角色设定要具体。对比一下:
- 弱设定:"你是一个编程助手"
- 强设定:"你是一位有十年经验的 Python 后端工程师,擅长 FastAPI 和数据库优化,回答时优先给出可运行的代码示例,并标注常见的性能陷阱"
强设定不仅告诉模型"你是谁",还隐含了"你该怎么回答"。这在 Agent 场景里尤其重要,因为 Agent 往往需要模型扮演特定职能角色,比如"客服意图分类器""代码审查员""数据分析师"。
2.2 任务指令:把"做什么"拆到不能再拆
任务指令是提示词的核心。我踩过最大的坑就是指令写得太笼统。比如"帮我分析这段代码的问题",模型可能给你返回一堆泛泛而谈的建议。但如果你写成"请检查以下 Python 代码中的三类问题:第一,是否存在未处理的异常;第二,是否有 SQL 注入风险;第三,变量命名是否清晰。按类别逐条列出,每条给出修改建议",输出质量立刻不一样。
拆解任务指令有个实用方法:问自己"如果我把这个任务交给一个新人,他需要知道哪些具体信息才能做好"。把这些信息全部写进指令里,基本就到位了。
2.3 输出格式约束:让结果可被程序消费
在 Agent 工作流里,模型的输出往往要传给下一个节点处理,所以格式约束不是"锦上添花",而是"必须项"。常见的格式约束方式有几种:
| 格式类型 | 适用场景 | 示例写法 |
|---|---|---|
| JSON | 结构化数据抽取、工具调用参数 | "以 JSON 格式输出,包含 name、type、confidence 三个字段" |
| Markdown 表格 | 对比分析、清单整理 | "用 Markdown 表格输出,列为:问题、严重程度、建议" |
| 分隔符分隔 | 简单列表、批量处理 | "每条结果用 --- 分隔,不要添加额外说明" |
| 固定标签 | 分类结果、枚举值 | "只输出以下之一:正面、负面、中性" |
格式约束要配合"反面约束"使用。比如你要求 JSON 输出,最好加一句"不要输出任何 JSON 以外的解释文字"。模型有时候会"好心"地加一段"以下是我的分析结果:",这在前端解析时就是灾难。
2.4 示例注入:少样本学习的威力
给模型几个输入输出示例,效果往往比写一大段规则描述还好。这叫少样本提示(Few-shot Prompting)。原理很简单:模型通过示例直接"看到"了你想要的输入输出映射关系,不需要从抽象规则里去推理。
示例的选择有讲究:
- 示例要覆盖典型情况和边界情况,不能只给"正常"的例子
- 示例的格式必须和真实输入完全一致,包括标点、换行、字段名
- 示例数量控制在 2 到 5 个,太少不够说明问题,太多浪费上下文窗口
- 示例的顺序有影响,把最重要的示例放在最后,模型对靠近输出的内容更敏感
我在做信息抽取 Agent 时,通常会给三个示例:一个标准情况、一个字段缺失的情况、一个包含干扰信息的情况。这样模型遇到各种输入都能稳住。
3. Agent 场景下提示词的特殊打法
3.1 系统提示词与用户提示词的分工
在 Agent 架构里,提示词通常分两层:系统提示词(System Prompt)和用户提示词(User Prompt)。系统提示词定义 Agent 的"人格"和"行为准则",用户提示词是每次调用时传入的具体任务。
分工原则是这样的:不变的规则放系统提示词,变化的输入放用户提示词。比如一个客服 Agent,系统提示词里写"你是一个电商客服助手,回答要简洁友好,不承诺无法兑现的售后政策,遇到退款问题引导用户提供订单号",用户提示词里则是具体的用户问题。
这样设计的好处是系统提示词可以复用,不用每次调用都重新构造。但要注意,有些模型对系统提示词的遵循度不如用户提示词高,关键约束可以在用户提示词里再强调一遍。
3.2 工具调用场景下的提示词设计
Agent 和普通聊天机器人最大的区别是能调用工具。工具调用的提示词设计有几个关键点:
第一,工具描述要精确。每个工具的用途、参数、返回值都要写清楚,模型才能正确选择。工具描述写得含糊,模型就会乱调或者不调。
第二,要在提示词里明确"什么时候该调工具,什么时候不该调"。比如"如果用户询问实时天气,调用天气查询工具;如果用户只是闲聊,直接回答,不要调用任何工具"。
第三,要处理工具调用失败的情况。提示词里加一句"如果工具返回错误,向用户说明情况并建议替代方案,不要编造数据",能避免很多幻觉问题。
3.3 多轮对话中的提示词状态管理
Agent 往往需要多轮交互,这就涉及对话历史的管理。把所有历史都塞进上下文,很快就会超出窗口限制;但丢太多历史,模型又会"失忆"。
我的做法是分层管理:最近 3 到 5 轮对话保留完整内容,更早的对话压缩成摘要。摘要的生成也可以用模型来做,提示词写成"请用一句话总结以下对话的核心信息和已确认的事实"。
另外,在多轮对话里要定期"重申"关键约束。比如一个订票 Agent,系统提示词里写了"确认订单前必须复述所有信息让用户确认",但在长对话中模型可能忘记。可以在每轮用户输入前,用系统消息再提醒一次关键规则。
4. 提示词翻车的典型场景与排查链路
4.1 输出格式不稳定:从解析失败反推提示词问题
这是最常见的翻车场景。你要求 JSON 输出,模型有时候给纯 JSON,有时候加一段解释,有时候字段名拼错。排查链路是这样的:
第一步,检查提示词里有没有明确的格式约束和反面约束。如果只写了"输出 JSON"而没有"不要输出其他内容",模型加解释是正常的。
第二步,检查示例。如果你给了示例,示例本身是不是严格的 JSON?模型会模仿示例的格式,示例不规范,输出就不规范。
第三步,检查温度参数。温度太高,格式稳定性会下降。结构化输出任务建议温度设到 0.2 以下。
第四步,考虑用模型提供的结构化输出功能。现在很多模型 API 支持 JSON Mode 或 Function Calling,能从底层保证格式,比纯靠提示词约束可靠得多。
4.2 指令遵循度低:模型"选择性失明"怎么办
有时候提示词里写了五六条规则,模型只遵循了前两三条。这不是模型"不听话",而是有几个可能的原因:
原因一,规则太多,超出了模型的"注意力分配"。解决方案是把规则按优先级排序,最重要的放最前面,或者拆分成多次调用。
原因二,规则之间有冲突。比如你既要求"回答要详细"又要求"回答不超过三句话",模型只能二选一。写提示词时要自查规则之间是否矛盾。
原因三,规则表述有歧义。中文的歧义性比英文高,写提示词时要尽量用明确的、无歧义的表述。比如"适当简化"就不如"删除所有形容词和副词"明确。
4.3 幻觉问题:提示词能做什么、不能做什么
幻觉是大模型的固有问题,提示词能缓解但不能根治。有效的缓解手段包括:
- 明确告诉模型"如果不确定,说不知道,不要编造"
- 提供参考资料,让模型基于资料回答,而不是靠记忆
- 要求模型给出信息来源或推理过程
- 在 Agent 场景里,用工具调用来获取事实性信息,而不是让模型"回忆"
但要清醒认识到,这些手段只是降低幻觉概率,不能消除。关键业务场景必须有后置校验环节。
5. 把提示词当代码来管理
5.1 版本控制与 A/B 测试
提示词改了之后效果变好还是变坏,不能靠感觉判断。我的做法是给每个提示词建版本号,每次修改记录改动内容和原因,然后用一组固定的测试用例跑对比。
测试用例要覆盖:正常输入、边界输入、异常输入。每次改提示词,跑一遍测试集,看通过率有没有下降。这套流程听起来麻烦,但比线上出问题再回滚要省事得多。
5.2 提示词模板化与参数注入
在实际项目里,提示词往往不是写死的,而是带参数的模板。比如"请分析以下{language}代码的{aspect}问题",调用时填入具体值。
模板化要注意两点:一是参数注入的位置要明确,避免歧义;二是要对参数做转义处理,防止用户输入的内容"越狱"提示词结构。比如用户输入里如果包含"忽略以上指令"这类文本,要有防护措施。
5.3 提示词长度与成本的平衡
提示词越长,消耗的 token 越多,成本越高,而且过长的提示词反而会降低模型对关键信息的注意力。我的一般原则是:能一句话说清楚就不写一段,能用一个示例说明就不写三条规则。
定期审查提示词,删掉那些"写了但从来没起作用"的内容。我每隔一段时间就会把线上提示词拿出来,逐条问自己"这条规则最近有没有实际影响过输出",没有的话就考虑删掉。
6. 从提示词到提示工程:建立系统化方法论
6.1 迭代式提示词开发流程
提示词不是一次写好的,是迭代出来的。我的开发流程大致是:
第一轮,写一个最小可用的提示词,能跑通基本流程就行。第二轮,用真实数据测试,收集失败案例。第三轮,针对失败案例修改提示词,补充约束或示例。第四轮,回归测试,确认修改没有引入新问题。循环二到四,直到通过率达到可接受水平。
这个流程的关键是"用数据驱动修改",而不是凭感觉调。每次修改都要有明确的失败案例作为依据。
6.2 不同模型的提示词适配
同一个提示词在不同模型上的效果可能差异很大。有的模型对系统提示词遵循度高,有的模型更依赖用户提示词;有的模型对格式约束敏感,有的模型需要更多示例。
做多模型适配时,建议把提示词拆成"通用部分"和"模型特定部分"。通用部分是任务描述和核心约束,模型特定部分是格式调整、示例数量、特殊标记等。这样切换模型时只需要改特定部分。
6.3 提示词工程的边界:什么时候该考虑微调
提示词工程有它的边界。当你发现无论怎么调提示词,效果都达不到要求时,可能就该考虑微调了。判断标准大致是:
- 任务非常垂直,通用模型缺乏领域知识
- 对输出格式和风格有极其严格的要求
- 提示词已经长到接近上下文窗口限制
- 有足够的标注数据用于微调
但微调不是万能的,它需要数据、算力和维护成本。大多数场景下,好的提示词工程加上合理的 Agent 架构,已经能解决百分之八十的问题。
7. 实操中积累的几个关键心得
7.1 提示词里的"负面指令"要慎用
"不要做什么"这类负面指令,模型遵循起来比正面指令差。心理学上有个说法叫"白熊效应"——你越说不要想白熊,越会想白熊。模型也有类似问题,你写"不要输出 Markdown 格式",它反而可能因为看到了"Markdown"这个词而输出 Markdown。
更好的做法是用正面指令替代负面指令。不说"不要输出解释",而说"只输出结果本身"。不说"不要编造数据",而说"只使用提供的资料中的信息"。
7.2 分隔符是提示词的"标点符号"
在提示词里用清晰的分隔符把不同部分隔开,能显著提升模型的理解准确度。常用的分隔符有三引号、XML 标签、Markdown 标题等。
比如:
### 任务 分析用户评论的情感倾向 ### 输入 """ 用户评论内容放在这里 """ ### 输出格式 只输出:正面 / 负面 / 中性这种结构让模型一眼就能看出哪部分是任务、哪部分是输入、哪部分是格式要求,比一大段连续文本清晰得多。
7.3 测试用例要"刁钻"一点
很多人写测试用例只写"正常情况",结果上线后遇到边界情况就翻车。我的经验是,测试用例里至少要有三成是"刁钻"的:空输入、超长输入、包含特殊字符的输入、语义模糊的输入、和任务无关的输入。
这些刁钻用例能帮你发现提示词的脆弱点。比如空输入时模型会不会崩溃,超长输入时会不会截断关键信息,特殊字符会不会破坏格式约束。
7.4 记录"提示词决策日志"
这是个容易被忽略但很有用的习惯。每次修改提示词,记录三件事:改了什么、为什么改、改后效果如何。过一段时间回头看,你会发现很多"当时觉得很重要"的修改其实没起作用,而一些"随手加的小改动"反而效果显著。
这份日志在团队协作时尤其有价值,能让其他人理解提示词里每条规则背后的意图,避免误删关键约束。
7.5 别忽视提示词的"可读性"
提示词是给人维护的,不是只给模型看的。写得乱七八糟的提示词,过两周自己都看不懂。建议用统一的格式规范:任务描述用一段话,约束条件用列表,示例用代码块,各部分之间用分隔符隔开。
可读性好的提示词,修改起来快,交接给同事也容易。这在长期项目里能省下大量沟通成本。
8. 一个完整的提示词设计实例拆解
8.1 需求场景描述
假设我们要做一个"代码审查 Agent",输入是一段 Python 代码,输出是结构化的审查意见。这个 Agent 需要识别代码中的潜在问题,按严重程度分类,并给出修改建议。
8.2 提示词初稿与问题分析
初稿可能是这样的:"请审查以下 Python 代码,指出问题并给出建议。"
这个提示词的问题很明显:没有角色设定,没有输出格式约束,没有严重程度分类标准,没有示例。跑出来的结果大概率是一堆泛泛而谈的建议,格式还不统一。
8.3 结构化改造后的提示词
改造后的版本:
### 角色 你是一位有十年经验的 Python 代码审查专家,熟悉 PEP8 规范、常见安全漏洞和性能优化技巧。 ### 任务 审查以下 Python 代码,识别问题并按严重程度分类。 ### 审查维度 1. 安全性:SQL 注入、命令注入、敏感信息硬编码 2. 健壮性:异常处理、边界条件、空值处理 3. 性能:循环效率、数据库查询、内存使用 4. 可读性:命名规范、注释、函数长度 ### 输出格式 以 JSON 数组输出,每个元素包含: - severity: "high" / "medium" / "low" - category: 问题类别 - line: 行号(如无法确定写 null) - issue: 问题描述 - suggestion: 修改建议 不要输出 JSON 以外的任何内容。 ### 示例 输入: """ def get_user(id): return db.query("SELECT * FROM users WHERE id = " + id) """ 输出: [ { "severity": "high", "category": "安全性", "line": 2, "issue": "SQL 语句通过字符串拼接构造,存在 SQL 注入风险", "suggestion": "使用参数化查询:db.query('SELECT * FROM users WHERE id = ?', [id])" } ] ### 待审查代码 """ {code} """8.4 改造前后的效果对比
改造前,输出是自由文本,格式不统一,问题分类模糊,经常漏掉安全问题。改造后,输出是标准 JSON,可以直接被程序解析,严重程度分类明确,安全问题基本不会漏。
这个例子的核心思路是:把模糊的需求转化为明确的维度、格式和示例。提示词工程的大部分工作,其实就是这个"翻译"过程——把人类脑子里的隐性要求,翻译成模型能明确执行的显性指令。
9. 提示词工程的持续精进路径
提示词工程不是学一次就够的技能,它随着模型能力的变化、业务场景的演进而不断更新。我自己的精进路径大致是三个阶段。
第一阶段是"能用就行",重点是跑通流程,理解提示词的基本结构。这个阶段多试多错,积累直觉。
第二阶段是"稳定可靠",重点是建立测试用例、版本管理、格式约束这些工程化手段。这个阶段的关键词是"可复现"。
第三阶段是"系统优化",重点是从单个提示词上升到 Agent 架构层面思考——什么时候该拆节点,什么时候该加工具,什么时候该上微调。这个阶段需要的是系统思维,而不是单点技巧。
回到 AI Agent 学习这条线,提示词和提示工程是绕不过去的基本功。Agent 的规划能力、工具调用能力、记忆管理能力,底层都依赖模型对提示词的理解和执行。把这一环打扎实,后面搭复杂 Agent 工作流的时候会顺畅很多。我在实际项目里最深的体会是:与其花时间追新框架,不如先把提示词写明白——框架会过时,但"把需求清晰地表达给模型"这个能力,会一直有用。