引用、拒答与冲突知识
正在读取学习记录…
引用是把回答中的事实连接到支持它的资料位置。可点击来源只是入口,还需要确认原文支持当前说法。依据不足时拒答是停止给出确定结论并说明缺什么;多份当前适用资料冲突时,应指出分歧并核实来源。
用退款资料观察引用
客户问退款期限。我们准备同一店铺两条当前政策,一条写三至五日,一条写二至四日。程序分别处理单一依据、冲突依据与空依据,并检查答案声称的期限是否真的来自引用。
days是天数范围,(3,5)表示三至五个工作日,(2,4)表示二至四个工作日。quote保存原文,id中的#到账标出所引用的规则位置。两份资料在演示中都按当前国内渠道规则处理,程序会把不同期限识别为冲突。
保存完整程序并运行
先在 PowerShell 创建并进入学习目录:
mkdir "F:\学习\l5-citation" -Force
cd "F:\学习\l5-citation"保存下面的文件后,在这个终端运行 dir 核对文件名,再执行本节给出的运行命令。
新建学习目录,例如 F:\学习\l5-citation。将下面代码完整保存为 citation_demo.py;代码包含固定资料和运行入口,保存后就能执行。
先在 PowerShell 创建并进入学习目录:
mkdir "F:\学习\l5-citation" -Force
cd "F:\学习\l5-citation"保存下面的文件后,在这个终端运行 dir 核对文件名,再执行本节给出的运行命令。
"""用结构化期限检查引用依据、资料缺失与当前规则冲突。"""
from dataclasses import dataclass
@dataclass(frozen=True)
class Evidence:
id: str
channel: str
days: tuple
quote: str
EVIDENCE = [
Evidence("P1#到账", "domestic", (3, 5), "退款通常三至五个工作日到账。"),
Evidence("P2#到账", "domestic", (2, 4), "退款通常二至四个工作日到账。"),
]
def answer(evidence, channel):
current = [item for item in evidence if item.channel == channel]
if not current:
return {"status": "资料不足", "days": None, "citations": []}
ranges = {item.days for item in current}
if len(ranges) > 1:
return {"status": "规则冲突", "days": None,
"citations": [item.id for item in current]}
return {"status": "有依据", "days": current[0].days,
"citations": [item.id for item in current]}
def verify(days, citations, evidence):
by_id = {item.id: item for item in evidence}
if not citations:
return False
# 每个引用必须存在,且支持所声称的同一期限。
return all(key in by_id and by_id[key].days == days for key in citations)
def main():
for label, items in (("单一依据", EVIDENCE[:1]), ("冲突依据", EVIDENCE), ("缺少依据", [])):
result = answer(items, "domestic")
period = str(result["days"]) if result["days"] else "待核实"
print(f"{label}:{result['status']};期限={period};引用={result['citations']}")
print("三至五日引用P1:" + str(verify((3, 5), ["P1#到账"], EVIDENCE)))
print("一天到账引用P1:" + str(verify((1, 1), ["P1#到账"], EVIDENCE)))
if __name__ == "__main__":
main()在保存文件的文件夹地址栏输入 powershell 并回车,再执行:
macOS:先在 Python 篇的学习文件夹中打开终端,执行 source .venv/bin/activate。再输入 cd ,把当前例子的文件夹拖入终端并回车,运行下面的命令。
cd "F:\学习\l5-citation"
ls
python -X utf8 citation_demo.py使用其他目录时,把第一行换成自己的路径。dir 应能列出 citation_demo.py。终端输出如下:
单一依据:有依据;期限=(3, 5);引用=['P1#到账']
冲突依据:规则冲突;期限=待核实;引用=['P1#到账', 'P2#到账']
缺少依据:资料不足;期限=待核实;引用=[]
三至五日引用P1:True
一天到账引用P1:False单一P1依据给出(3,5)和明确引用位置;两份同渠道规则的期限不同,结果列出两个引用并把期限留为待核实;空依据也留为待核实。最后两行检查同一引用是否支持说法:三至五日通过,一天到账失败。引用存在与结论受支持在这组输出中分开检查。
从原文到回答事实的核对
Evidence保存引用位置、适用渠道、提取的天数范围和原文。answer先按渠道取资料,再比较天数集合;只有同一范围才输出确定期限。冲突和资料不足分别返回状态,调用方可以用它们决定核实政策还是补充检索。
verify检查引用编号存在,且每条引用的结构化天数都与答案一致。它能发现这组期限事实的编造和引用错配。天数是预先从固定规则提取的,真实文本还需要核对提取是否正确、工作日还是自然日、期限从申请还是审核通过开始,以及商品和渠道例外。
多份资料冲突时,先核查适用范围、生效时间和正式来源优先级。旧政策与新政策并存但生效时间不同,可以按经过验证的版本规则选择;同时有效且来源权威相当的冲突,应列出分歧并转业务负责人核实。此处两份固定资料都按当前国内规则处理,所以保留冲突状态。
拒答可以写成“已查到的国内政策出现三至五日和二至四日两种期限,需要核实当前规则”,并附对应原文。缺资料时说明需补充的订单渠道或政策,不用凭模型常识填空。部分问题有依据时,可以回答受支持部分,把待核实部分明确分开。
引用覆盖检查多少事实附有支持位置,引用正确性检查原文是否支持事实,两者不能互相替代。回答中数字、对象、条件、否定词都需要逐条核对。工具可以检查编号和字段,开放文本的含义还需要更细的规则、人工核对或经过评估的验证器。
改一处输入,核对机制变化
把EVIDENCE第二项的 (2, 4) 改为 (3, 5),同时把原文改为“退款通常三至五个工作日到账。”,运行 python -X utf8 citation_demo.py。第二行变为有依据、期限(3,5),仍列出两条引用;最后一天到账检查仍为False。恢复范围与原文后重跑,两份当前规则再次触发冲突。
运行配套检查
把下面测试保存为 test_citation_demo.py,与主程序放在同一目录。5项测试检查上面的实际处理结果,也覆盖规则冲突、缺少依据和引用错配。
查看测试代码:test_citation_demo.py
"""核对引用、拒答与冲突知识的正常结果与具体边界。"""
import unittest
import citation_demo as demo
class DemoTests(unittest.TestCase):
def test_single_supported_answer(self):
# 单一依据支持准确期限。
result = demo.answer(demo.EVIDENCE[:1], "domestic")
self.assertEqual((result["status"], result["days"]), ("有依据", (3, 5)))
def test_conflict_does_not_choose_arbitrary_period(self):
# 冲突列出双方引用,不能任取一个期限。
result = demo.answer(demo.EVIDENCE, "domestic")
self.assertEqual(result["status"], "规则冲突")
self.assertIsNone(result["days"])
self.assertEqual(len(result["citations"]), 2)
def test_no_applicable_evidence(self):
# 无适用渠道资料时返回资料不足。
self.assertEqual(demo.answer(demo.EVIDENCE, "overseas")["status"], "资料不足")
def test_fabricated_period_and_reference_are_rejected(self):
# 编造期限、编造编号和空引用都无法通过。
self.assertFalse(demo.verify((1, 1), ["P1#到账"], demo.EVIDENCE))
self.assertFalse(demo.verify((3, 5), ["missing"], demo.EVIDENCE))
self.assertFalse(demo.verify((3, 5), [], demo.EVIDENCE))
def test_correct_period_matches_every_citation(self):
# 每条引用均需支持同一期限。
self.assertTrue(demo.verify((3, 5), ["P1#到账"], demo.EVIDENCE))
self.assertFalse(demo.verify((3, 5), ["P1#到账", "P2#到账"], demo.EVIDENCE))
if __name__ == "__main__":
unittest.main()python -X utf8 -m unittest -v test_citation_demo.py测试名称后应显示 ok,末尾是 Ran 5 tests 和 OK。
运行时怎样定位问题
| 看到的情况 | 检查与操作 |
|---|---|
| 找不到 citation_demo.py | 运行 dir,切换到保存主程序的目录 |
| 有来源链接却答错期限 | 对照原文与答案字段,检查引用是否支持说法 |
| 冲突规则被强行平均 | 按有效范围与权威版本核实,保留冲突状态 |
| 缺资料时给出常识答案 | 返回资料不足,说明缺的渠道、版本或政策 |
引用依据核对后,可以继续研究多步检索、层级索引和更复杂的资料组织。
参考阅读:LlamaIndex 源码与检索流程。阅读时可以沿文档、节点、索引和检索入口对照这里的数据流。
课后练习展开习题收起习题
正在读取本地记录…
不调用模型,不执行代码。简答、代码和场景题仅保存答案并展示自查标准,不生成评分、徽章或认证。输入内容不会自动保存,请点击提交;不要填写个人信息或密钥。
选择题 · 先判断边界
关于“引用、拒答与冲突知识”,哪种做法更稳妥?
对应知识点:L5-citation
简答题 · 解释失败
写出一个失败输入并说明记录字段。
对应知识点:L5-citation
代码题 · 边界测试
补充正常、边界、失败三组输入和预期结果。
对应知识点:L5-citation
场景题 · 结果未知
证据不足时如何设计状态和人工接管?
对应知识点:L5-citation
下一篇:高级 RAG 策略。
描述会发送给本站维护者,用于修订文章,保存90天。请只填写文章问题,省略个人信息、密钥和内部资料。