封闭域问答系统的目标很明确:模型只能依据给定的文档回答问题,不能使用训练阶段学到的外部知识。但实际部署中,模型常常在文档信息不足时自行补全,甚至把相关性不高的段落当成证据。要让模型稳定地在文档内推理,提示词需要同时完成三件事:划定证据范围、规定推理路径、要求显式引用。下面从一个最简单的提示词开始拆解。

一、封闭域问答和开放域问答的关键差异
封闭域问答也被称为给定文档问答或阅读理解式问答。它的前提是答案必须存在于一个明确的文档集合中,模型不能调用参数化记忆来回答。开放域问答则相反,模型可以先从外部知识中找到候选信息,再综合生成答案。这个差异看似简单,但在提示词层面会带来完全不同的设计目标:封闭域提示词的首要任务是限制信息边界,而不是激发模型的知识联想。
很多失败案例表明,即使文档里已经包含正确答案,模型仍然可能选择一个更符合常识但与文档矛盾的说法。例如文档写某版本发布时间是三月,模型因为训练数据中常见的是四月,就输出四月。这种参数化记忆干扰在开放域场景中影响较小,但在需要审计和溯源的企业知识库、合同审查、医疗文献辅助阅读中是不可接受的。因此,提示词不能只说根据文档回答,而要设计一套可验证的推理约束。
为了让限制真正生效,还需要区分两个概念:生成约束和推理约束。生成约束只限制最终答案的来源,比如禁止说文档没有的内容;推理约束则进一步规定中间步骤如何从原文抽取事实、如何组合证据。后者更难,但它是提升多跳问题准确率的关键。
二、推理提示词的核心结构:角色、证据、步骤、输出格式
一个可用的封闭域问答提示词通常包含四个部分:角色与目标、文档边界、推理步骤、输出格式。角色部分不必写得过于戏剧化,但需要明确回答者身份和限制。文档边界要说明只有给定内容可用,且不能用记忆补充。推理步骤要具体,尤其是当问题需要跨句或跨段推理时。
下面是一个基础模板,使用Python字符串形式展示,方便直接集成到RAG流程中。
prompt = """
你是一个严格的封闭域问答助手。你的回答只能依据【文档】中的内容,不得使用任何外部知识或训练记忆中获取的信息。
【文档】
{document}
【问题】
{question}
请按以下步骤完成:
1. 从文档中找出与问题直接相关的句子,原文摘录,并标注段落编号。
2. 如果问题需要多步推理,先写出每一步的中间结论,并说明依据。
3. 最后给出最终答案。每个关键结论后必须标注证据位置,格式为 [段落编号]。
4. 如果文档信息不足或存在矛盾,请回答:信息不足,无法回答。
"""
这个模板中的第4步很关键。它把拒答从一种失败处理变成正常输出类别,这样模型不会为了给出答案而强行关联不相关段落。实际测试中,加入明确的拒答条件后,错误补全的比例会明显下降。
另一个容易被忽略的点是证据标注格式。要求模型用[段落编号]标注,会让模型在生成时更倾向于回到原文查找依据,而不是凭感觉作答。但要注意,段落编号必须由检索或切分阶段稳定提供,否则模型会自己编造编号。
三、多跳问题的推理链设计
单跳问题只需要定位一个事实,提示词简单也能取得不错效果。多跳问题需要组合两个以上信息点,比如文档中A段说某产品在2023年发布,B段说该产品发布后三个月推出升级版,问题是升级版在哪一年推出。如果直接让模型回答,它可能跳过中间计算直接猜一个年份。此时需要强制显式推理链。
可以修改步骤部分,要求模型输出一个编号列表:第一步找到产品发布时间,第二步找到升级间隔,第三步计算年份。这样即使最终答案错误,也能根据中间步骤定位是哪一步抽取失败。
prompt = """
请只基于【文档】回答下面的多跳问题。
【文档】
{document}
【问题】
{question}
推理要求:
- 先列出问题中所有需要确认的实体或属性。
- 逐个在文档中查找对应事实,并标注段落编号。
- 如果某个中间事实缺失,立即停止并回答:信息不足,无法回答。
- 每一步中间结论必须单独写出,禁止跳步直接给最终答案。
- 最终答案单独一行,格式为:答案:xxx
"""
这种强制分步的设计会增加输出长度,但对复杂问题的收益非常明显。代价是推理时间变长,因此不需要对所有问题都使用多跳模板。可以通过一个轻量级分类提示词判断问题是否需要多跳,或者根据关键词和问句结构做规则分流。
多跳推理中还有一个常见问题:模型会把不同实体的属性错误拼接。比如文档中A公司成立于2010年,B公司成立于2015年,问题是A公司和B公司谁更早成立。如果只要求引用,模型可能分别引用两段但仍比较错误。更好的做法是让模型先列出两个年份,再进行比较运算,最后给出结论。比较类问题尤其需要显式中间值。
四、常见失败模式与调优策略
封闭域问答的失败模式并不总是模型能力不足,更多时候是提示词没有覆盖到边界情况。第一类失败是外部知识混入。模型在文档证据不完整时,会补充一个训练数据中的常见答案。解决办法除了加入拒答条件,还可以在提示词中加入反向检查:在给出答案前,确认答案中的每个实体和数字是否都能在文档原文中找到对应表达。
第二类失败是否定表达被忽略。文档写的是该系统不支持实时同步,但问题问是否支持实时同步时,模型可能只看到实时同步就回答支持。可以在提示词中增加一步:先判断文档中对相关属性是肯定、否定还是未提及,再作答。这个简单步骤能显著减少极性反转错误。
第三类失败与文档切分有关。实际RAG系统会把长文档切成小块,如果问题答案跨越两个块,单一上下文可能不够。提示词虽然不能直接解决检索问题,但可以通过要求模型显式列出缺失信息,帮助上游模块发现需要补充检索的块。例如模型回答信息不足,并注明缺少某实体的时间信息,检索模块就可以用这个信号进行二次检索。
第四类失败是输出格式不稳定。如果下游需要结构化结果,最好在提示词中给出JSON或固定格式示例,而不是只描述格式要求。文本模型对示例的遵循程度通常高于抽象描述。一个小的格式示例胜过一段格式说明。
五、工程落地建议
在工程实现中,提示词应作为配置项管理,而不是硬编码在业务代码里。不同文档类型、不同问题类型可能需要不同模板。建议将提示词模板、模型参数、检索参数放在同一配置中,方便A/B测试和版本回滚。
评估封闭域问答时,除了最终答案是否正确,还应关注证据引用是否真实存在。可以增加一个证据校验步骤:抽取模型引用的段落内容,判断是否真的支持结论。如果引用无效但答案正确,只能算部分正确,因为这种正确可能是运气或外部知识带来的。
最后,提示词不是越严格越好。过于复杂的约束会消耗模型的指令遵循能力,导致格式错误或拒答率过高。设计时应从最小约束开始,逐步增加步骤,通过小样本评测观察指标变化。一个好的封闭域问答提示词,最终效果是让模型在给定文档内保持推理透明、可追溯、可纠正。