AI小说工厂(三):编辑部——AI自己审稿的闭环设计

  • ~4.74K 字

记忆解决遗忘,但不解决写得烂。这篇讲质量闭环的另一半:一致性审查怎么设计才不沦为走过场、七维评审的裁决标准怎么定、硬规则引擎为什么必须确定性、伏笔账本怎么治”埋了不收”的老毛病。

一致性审查:从”打印报告”到”自动修复”

AI_NovelGenerator 原版的一致性审查有个通病:审查结果只打印出来,没人处理。报告说”第 2 章死者人数与第 1 章矛盾”,然后呢?然后没有然后了。

我的设计是闭环:审查 → 有问题 → 定向修复 → 复审。看真实流程:

草稿 → 一致性审查(LLM 结构化判定 JSON)
→ 无 serious 问题 → 定稿
→ 有 critical/major → 自动修复一轮(带审查报告做指引) → 复审
→ 通过 → 定稿
→ 仍不通过 → 记录在案,仍定稿(避免无限循环)——留给人看

两个关键裁决逻辑(从早期 bug 里学来的):

  1. 判定以 severity 为准,不信模型自报的 pass 标志。早期版本同时有 pass 布尔和 issues 列表,两者矛盾时以 pass 为准——结果模型嘴上说通过、列表里躺着两个 critical。改成只看 severity:critical/major 触发修复,minor 记录不阻断
  2. 修复是有界的。最多一轮修复一次复审,修不好就带着问题定稿并显式记录。AI 审查 AI 的修复效果存在边际递减,无限循环只是烧 token

真实战绩:项目第二次端到端验证时,第 2 章审查发现 2 个 major(伏笔冲突:某角色未出场就互动 + 设定矛盾:死者名单口径不一)+ 1 个 minor(物件位置前后不一),自动修复后复审通过——闭环不是摆设,它真的在拦东西

还有一个静默 bug 值得记录:一致性审查函数有个参数没传对,导致它自上线起就一直静默跳过——日志显示”审查通过”,实际是根本没审。这暴露了”跳过”和”通过”在日志上必须有区分度,后来所有可跳过步骤的日志都带显式的 skip 标记。

七维评审:编辑部的总闸

逐章的一致性审查管”对不对”,七维评审管”好不好”。这是从 ainovel-cli 的 editor 设计吸收改造的,直接输出结构化 JSON:

EDITOR_REVIEW_SYS = """你是小说全局审阅者(编辑)。必须基于章节正文本身评审,
不得只看摘要下结论。输出 JSON:
{"overall": 0-100总分,
"dims": {"设定一致性": {"score": 0-100, "evidence": "引用一句原文作依据"},
"人设一致性": {"score": 0-100, "evidence": "..."},
"节奏平衡": {"score": 0-100, "evidence": "..."},
"叙事连贯": {"score": 0-100, "evidence": "..."},
"伏笔健康": {"score": 0-100, "evidence": "..."},
"钩子质量": {"score": 0-100, "evidence": "..."},
"审美品质": {"score": 0-100, "evidence": "..."}},
"verdict": "rewrite或polish或accept",
"notes": ["最重要的问题与修改建议,每条注明位置"]}

判定:
- 审美品质按「本书文风要求」的句式/对话/节奏维度判断,必须引用原文举证
- verdict 标准:任一维 <50 或 overall<60 → rewrite;
overall<70 或两维 <65 → polish;否则 accept
(accept 是最常见结果,不要为了显得严格而降级)
- 证据不足不要硬凑分;伏笔健康在本书前 3 章可给中性分(伏笔尚未展开)

这段提示词里藏着四个裁决智慧:

  • “必须基于章节正文本身评审,不得只看摘要下结论”——LLM 审稿最爱犯的错是看着摘要脑补评价,这句话 + 输入里真实放正文双保险
  • “accept 是最常见结果,不要为了显得严格而降级”——LLM 当评审有”表演严格”的倾向(觉得不挑几个毛病显得没干活),显式校准它的先验
  • “前 3 章伏笔健康可给中性分”——不是所有维度在所有章节都有意义,给模型免责条款,防止硬凑分
  • 每条意见必须引用原文举证——evidence 字段强制审稿人”贴出原文”,杜绝空泛的”节奏略显拖沓”

verdict 三档对应三种处置:rewrite 推倒重写本章、polish 定向打磨、accept 直接过。评审不是每章都跑——那是烧钱大户,实际节奏是关键章节 + 抽查 + 夜间批量的可选环节。

**失败裁定(Arbiter)**是评审的最后一环:rewrite 之后质量分还是上不去,谁来裁决”继续重写”还是”接受现状继续推进”?再打一次分的 LLM 裁定,输入是历次评审报告 + 重写差异,输出是裁决和理由。升级裁判而不是无限重赛,这是对”有界修复”思想的延伸。

硬规则引擎:确定性的部分就该交给确定性

LLM 评审再好,也有它不该管的领域——禁词就是禁词,数一遍就知道有没有,让 LLM 判断”是否包含’系统面板’四个字”是用大炮打蚊子还可能打偏。硬规则引擎是纯确定性的:

def check(text: str, rules: dict) -> list:
"""确定性机械检查:只返回违规事实。
forbidden=error(需修复);fatigue=warning(记录+评审参考)。"""
out = []
for ph in rules.get("forbidden_phrases") or []:
n = text.count(ph)
if n:
out.append({"rule": "forbidden", "target": ph, "actual": n,
"severity": "error"})
for w, limit in (rules.get("fatigue_words") or {}).items():
n = text.count(w)
if n > limit:
out.append({"rule": "fatigue", "target": w, "limit": limit,
"actual": n, "severity": "warning"})
return out

规则的书写格式是行式的,用户在设定页直接写人话:

禁止:后宫、系统面板
疲劳词:不由得≤2、眼底闪过≤2
偏好:多对话,快节奏

三种语义三个处置:禁止是 error,违规触发定向重写(只重写含违规词的段落,不是整章重来);疲劳词是 warning——AI 写作的高频病(”不由得””一丝””眼底闪过”这类词 AI 特别爱用),超限记录并作为评审参考,不硬拦;偏好注入每次写作的提示词。

这里有个”行式解析 + LLM 归一化”的双层设计:用户随手写的规则先过一遍确定性解析(格式规范的直接用),模糊的再让 LLM 归一化成结构化规则。LLM 处理模糊性,确定性引擎执行判断——各干各的擅长事。

伏笔账本:治”埋了不收”的账本式解法

埋伏笔容易,收伏笔难——AI 尤其如此,因为它压根不记得埋过。事实卡系统在每个章节定稿时结构化提取事实(时间线/伏笔操作/关系变化/状态变化),其中伏笔操作带三种动作:

plant   埋设:建账(伏笔内容 + 埋设章号)
advance 强化:更新最近强化章号
resolve 回收:销账(记录回收章号)

账本的查询端是 active_foreshadows(pid)——聚合全部事实卡,返回所有”已埋未收”的活跃伏笔。这份清单注入三个地方:后续草稿的上下文(提醒写作模型有账要收)、一致性审查(”这个伏笔埋了 40 章了没收”)、蓝图滚动窗口(新窗口规划时优先安排回收)。

一个真实的反面教材驱动了上限设计:早期版本 10 章埋了 45 条伏笔——每章 plant 无上限,AI 又特别爱埋伏笔显深度,账本爆炸。修复是双管齐下:提示词限定伏笔纪律 + 每章 plant ≤ 3 的机械上限。账本不仅要记账,还要管住记账的手

踩坑小结

  • “跳过”和”通过”必须有区分度。一致性审查静默跳过的 bug 之所以潜伏,就是因为两者日志长得一样。所有可选环节的日志都要带显式 skip 标记
  • 不信模型自报的状态,信结构化的证据。pass 标志会和 issues 矛盾,severity 不会——判断逻辑要建立在可枚举的字段上
  • 给评审校准先验。”accept 是最常见结果”这句话值很多钱,没有它 LLM 评审会系统性地表演严格
  • 确定性的事交给确定性。禁词检查、字数统计、伏笔账龄,全是不需要智能的判断,text.count() 比任何 LLM 都可靠且免费
  • 修复必须有界,重赛不如升级裁判。AI 修 AI 的边际效果递减很快,一轮修复一次复审,不行就带病定稿留给人

小结

编辑部这套闭环的本质是把”质量问题”拆成了三种性质不同的东西:矛盾(一致性审查管,可自动修复)、好不好(七维评审管,给裁决建议)、红线(硬规则管,机械执行)。下一篇讲质量体系的最后一块——连”爽不爽”这种主观感受,也想办法变成了确定性分数。

赞助喵
非常感谢您的喜欢!
赞助喵
分享这一刻
让朋友们也来瞅瞅!