🧠 第十一章 医疗与法律:重塑精准诊疗与服务流程
📄 一句话概括

12 条必备条款 × 200 份合同 = 2400 次判断。漏检 199 处,全部来自「换了说法但词表里没有」; 误判 20 处,全部来自「提到了但明确说不适用」。 补全同义词表后漏检从 199 掉到 0,误判一处没动。 准确率 90.9% 到 99.2%——剩下那 0.8% 是词表碰不到的。

📝 本节和前面几节的关系

前两节是律所和法院的视角。这一节换成企业法务:合同签之前,逐条核对必备条款。 这是法律 AI 落地最实在、也最容易做砸的一个场景。

一、合规检查本质是清单核对

企业的合同审查,很大一部分不是「判断」,是「核对清单」。 这份合同有没有约定争议解决方式?有没有保密条款?有没有不可抗力?有没有知识产权归属? 这类问题有标准答案,而且答案是「有 / 没有」二值。 所以它天然适合规则,不适合大模型—— 大模型给的是「这段话大概在讲保密」,而法务要的是「第 7 条有没有」。 规则引擎在这个场景里还有两个决定性优势: ① 结果可解释。 命中了哪个词、在第几段,一目了然。 ② 快。 Demo 里 2400 次判断只花不到 2 毫秒。 这意味着可以在合同起草界面上做实时提示,而不是等一晚上出报告。 但规则有个绕不过去的软肋:它只认字面。 而合同恰恰是一种「同一个意思有一百种说法」的文体。这一节就来看这两种错怎么发生。

二、假阴性:换了说法,关键词躲开了

条款 真存在 真缺失 漏检 补词后 误判
合同主体 166 34 0 0 0
标的描述 167 33 0 0 0
价款金额 165 35 0 0 0
付款方式 162 38 0 0 0
交付时间 163 37 0 0 0
质量标准 168 32 0 0 1
违约责任 164 36 30 0 4
争议解决 166 34 36 0 4
保密条款 176 24 34 0 5
不可抗力 172 28 33 0 4
知识产权 161 39 33 0 2
合同期限 171 29 33 0 0
先看「漏检」那一列:一共 199 处,全部来自「换了说法但词表里没有」。
比如「违约责任」被写成「违约赔偿」——意思一模一样,字一个不差地躲开了关键词。
「保密条款」被写成「信息保护义务」,同一个道理。
这就是假阴性:条款明明在,机器说没有。
它的危险在于「静默」——法务看到的是一份「缺 5 条」的报告,而实际只缺 2 条,
多出的 3 条是误报。
看多了之后,人就会开始忽略这个报告的警告。
这 199 处漏检全部分布在后 7 条上,前 5 条一条都没有。
为什么?因为前 5 条的表述高度固定(甲方、标的、价款、付款方式、交付时间),几乎没人换说法;
而后 7 条的表述本身就在演化。
这一点很值得注意:漏检不是均匀分布的,它集中在「表述最灵活的那几条」。
所以补词表也应该按条款分别投入,而不是平均用力。

三、假阳性:词在,意思反了

把同义词补进词表之后,漏检从 199 掉到 0。 但「误判」那一列一动不动,还是 20 处。 因为误判的来源不是「词表不全」,是「提到了但明确说不适用」。 比如「本合同不约定争议解决方式」——关键词「争议解决」在,但它恰恰是在说这一条没有约定。 再比如「本合同不设保密义务」——「保密」两个字响亮地在场,意思完全相反。 这类否定语境,关键词规则从原理上就判不了。 因为它需要判断「这个短语的极性」,而不是「这个短语在不在」。 补词表只会让它误判得更起劲,因为能撞上的词更多了。 这就是假阳性:条款明明不在,机器说在。 它的危险和假阴性对称——一个让法务漏看,一个让法务白看。 但在合同场景里,假阳性更常见,因为起草人经常用「本合同不适用 XX」来主动排除某一条。 补词表把标出量从 578 砍到 379,砍掉的全是漏检;剩下那 20 处误判,按词表怎么补都补不掉。 379 处里 359 处真缺、20 处是误判——误报率 5.3%,这个水平是法务可以接受的。

四、规则引擎的定位:筛,不判

「准确率 90.9% 到 99.2%」这个提升听起来很好,但更该看的是那 0.8%。 这 0.8% 是「词表碰不到的」,它不会因为再多加几百个同义词而消失。 所以规则引擎的正确定位是:负责筛,不负责判。 它把 2400 条判断筛成 379 条「疑似缺失」,让人只看这 379 条,而不是看全部。 人省下的是 84% 的时间,不是 100% 的时间。 这个定位决定了两件事: ① 阈值要偏向「宁可多报」。 漏检的代价远高于误报—— 漏了一个真缺的条款,合同签了就是风险;多报一个误判,律师扫一眼就过去了。 ② 报告要分组,不要给一个总分。 「合规分 92 分」这种输出没有操作性。 有用的是「争议解决、保密条款、不可抗力这三条缺失,请确认」。 补充这两个字的边界:什么时候该上模型? 当假阳性和假阴性同时高到人看不过来的时候。 如果 379 条里只有 20 条是误判,人看得过来,就没有必要引入模型—— 引入模型会带来新的不确定性,而且结果不好解释。 「能用规则就别上模型」在合规场景里是一条很实在的经验。

五、落地:四步

① 条款清单要来自业务,不是来自模板。 不同行业、不同金额、不同交易对手,必备条款不一样。 一条全院通用的清单,通常意味着每条都不够细。 ② 词表按条款分别维护,并记录「这条为什么加」。 否则半年后没人敢删任何一个词,词表会膨胀成垃圾场。 维护记录本身就是这个系统最有价值的资产。 ③ 否定语境单独处理。 做一个简单的否定词前置检查:「不」「无」「另行」「除外」等词出现在关键词前 10 个字符内时, 降级为「待人工确认」。 这一条能消掉大部分假阳性,而且不需要模型。 ④ 把复核结果回流。 律师每一次「这条其实是有的」都应该变成一条新的同义词。 这个闭环跑起来之后,词表会自己长大——而它长大的方向,恰好是这个企业真实的合同写法。 最后一句:合规检查的价值不在「查出多少问题」,在「让该看的被看到」。 按这个标准衡量,一个会误报但从不漏报的系统,比一个准确率高但会静默漏检的系统有用得多。

六、动手 Demo:合同合规检查:补全同义词表,准确率从 90.9% 到 99.2%

造 200 份合成合同,每份随机保留 8 到 12 条必备条款(共 12 条清单)。 存在的条款有 20% 概率被换成「词表外的同义表述」, 缺失的条款有 10% 概率插入一句「本合同不约定 XX」的否定句。用关键词规则逐条判断,统计漏检、误判; 再把同义词补进词表重算,看两类错误各变化多少,并测总耗时。

def check(txt, extra):
    out = set()
    for j, (name, words) in enumerate(CLAUSES):
        ws = list(words) + (ALIAS.get(name, []) if extra else [])
        if any(w in txt for w in ws):       # 命中任一就算「有」
            out.add(j)
    return out

if j in pres and j not in got:      # 漏检
    fn[j] += 1
elif j not in pres and j in got:    # 误判
    fp[j] += 1

实跑输出:

--------------------------------------------------------------------
合同合规检查:补全同义词表,准确率从 90.9% 到 99.2%
--------------------------------------------------------------------
  合同数                   200 份,每份随机缺 0~4 条必备条款
  规则条数                 12 条,每条 2~3 个关键词
  判断次数                 2400 次(200 份 × 12 条)
  纯规则总耗时             1.8 毫秒

  条款       真存在   真缺失   漏检   补词后漏检   误判
  ----------------------------------------------------
  合同主体      166       34      0            0      0
  标的描述      167       33      0            0      0
  价款金额      165       35      0            0      0
  付款方式      162       38      0            0      0
  交付时间      163       37      0            0      0
  质量标准      168       32      0            0      1
  违约责任      164       36     30            0      4
  争议解决      166       34     36            0      4
  保密条款      176       24     34            0      5
  不可抗力      172       28     33            0      4
  知识产权      161       39     33            0      2
  合同期限      171       29     33            0      0

  **先看「漏检」那一列:一共 199 处,全部来自「换了说法但词表里没有」。**
  比如「违约责任」被写成「违约赔偿」——**意思一模一样,字一个不差地躲开了关键词。**
  「保密条款」被写成「信息保护义务」,同一个道理。
  把同义词补进词表之后,**漏检从 199 掉到 0。**
  **但「误判」那一列一动不动,还是 20 处。**
  **因为误判的来源不是「词表不全」,是「提到了但明确说不适用」。**
  比如「本合同不约定争议解决方式」——**关键词「争议解决」在,但它恰恰是在说这一条没有约定。**
  再比如「本合同不设保密义务」——**「保密」两个字响亮地在场,意思完全相反。**
  **这类否定语境,关键词规则从原理上就判不了。**
  **补词表只会让它误判得更起劲,因为能撞上的词更多了。**
  **这就是规则引擎在合规场景里的真实定位:负责筛,不负责判。**
  **200 份合同 2400 次判断只花 1.8 毫秒**,机器标出 379 处「疑似缺失」。
  **这 379 处里,359 处真缺、20 处是误判。**
  **补词表把标出量从 578 砍到 379,砍掉的全是漏检;**
  **剩下那 20 处误判,按词表怎么补都补不掉。**
  **最后那一步仍然是律师签字。**
  要说明:合同是我**按条款词拼接生成的**,**真实合同的条款会分散在附件、补充协议、往来函件里**。
  **但「假阴性靠补词表、假阳性靠语义理解」这个分工是真的。**

done -> _out_39t.txt

这张表要横着读:先看「漏检」,再看「补词后漏检」,最后看「误判」。 第一列找到 199,第二列归零,第三列纹丝不动——这三步就是整个故事的骨架。 注意前 5 条的漏检和误判都是 0。 这不是巧合:这 5 条的关键词(甲方、标的、价款、付款方式、交付时间)是合同里最固定的表述, 几乎没人改写。 所以补词表的正确姿势是「按条款分别投入」,而不是「整体多加几百个词」。 误判那 20 处全部集中在 6 条上,而且都是否定句造成的。 「本合同不约定违约金」——「违约金」在,意思相反。 这类错误靠词表永远治不好,必须另做一层否定检测。 耗时那一项是每次跑都不一样的(本机在 1.8 到 2.4 毫秒之间浮动), 所以正文里只说「不到 2 毫秒量级」。 它的意义不是「有多快」,是「快到可以嵌进实时界面」。 要说明:合同是我按条款词拼接生成的, 真实合同的条款会分散在附件、补充协议、往来函件里,还会互相引用(「按第 3 条约定的方式」)。 但「假阴性靠补词表、假阳性靠语义理解」这个分工是真的。

30 秒实验

  1. 把同义替换的概率从 20% 提到 50%,看漏检那一列。 会大幅上升——表述越自由,漏检越多,这是规则方法的固有上限。
  2. 给检查器加一条简单规则:关键词前 10 个字符内出现「不」「无」「另行」就判为待确认。 误判会明显下降,但会引入少量新的漏检——否定检测本身也有误差。
  3. 把必备条款从 12 条加到 30 条,看总耗时和误判数。 耗时仍在线性增长且极快,但误判数会上升——条款越多,撞词的机会越多。

常见误区

  1. 「补全同义词表就能解决问题」。漏检确实归零,但那 20 处误判一处没动。
  2. 「提到了就说明有」。「本合同不约定违约金」里「违约金」在,意思相反。
  3. 「准确率 99% 就可以全自动」。剩下那 0.8% 是词表碰不到的,而且恰恰是最需要人判断的部分。
自测三问(点开对答案) 1. 假阴性和假阳性在这个 Demo 里各自怎么产生? —— 假阴性来自「换了说法、词表没收录」;假阳性来自「提到了但明确说不适用」的否定句。 2. 为什么补词表能治一种、治不了另一种? —— 补词表增加的是「能命中的字面」,对假阴性有效;误判需要判断极性,词表多反而撞得更多。 3. 在合规场景里,为什么应该偏向「宁可多报」? —— 漏检会让风险随合同签下去,误报只是律师多扫一眼。两者代价不对等,阈值就该往多报那边偏。

第十一章讲完了: 从数据、知识、算力,到诊断、管理、法务。这一整章反复出现的判断是「指标必须带上场景」。 最后一章换到金融与农业——那两行的共同点是:预测一旦被相信,就会自己改变结果。

相关笔记