← 返回 PaperDaily 大模型与智能体

MIRA让SQL纠错记忆精准复用:修复261条错查询仅误伤18条

Text-to-SQL最磨人的不是不跑,而是“跑得动、结果是错的”。MIRA把历史修正记忆拆成乐高式独立修复项,再用数据库证据精准激活——261次成功修复、仅18次误伤,SQL纠错玩出了手术级精度。

MIRA让SQL纠错记忆精准复用:修复261条错查询仅误伤18条

paperdaily_reaction_gif


原论文信息如下:
论文标题:
MIRA: Evidence-Verified Repair Memory for Text-to-SQL Correction
发表日期:
2026年08月
发表单位:
北京理工大学(珠海)、香港科技大学(广州)、深圳大学
原文链接:
https://arxiv.org/pdf/2608.06950v1.pdf

261次修复仅18次误伤!MIRA把Text-to-SQL纠错玩出精度新高地

Text-to-SQL 最近有多火?办公室里那帮天天写报表的数据分析师,都已经开始让大模型帮忙写 SQL 查数了。但真正让从业者头皮发麻的场景,永远是那种“看起来一切正常,跑出来的结果却是错”的情况——SQL 没有任何语法错误,执行器也欢快地跑完了,可返回的数据就是不对。按照评测标准,这属于执行结果与标准查询不匹配,执行准确率为 0。更麻烦的是,在一个生产级数据库里,用户关心的根本不是你 SQL 写得多优雅,而是它给的结果到底靠不靠谱。
问题出在哪?大模型做 Text-to-SQL 时,经常“脑补”出和原问题含义不符的查询逻辑——比如漏掉一个去重、多加了一个过滤条件、表连接方式不对——但语法完全合法,执行结果悄悄就错了。这类错误靠模型自我纠正确实难搞:一个生成错了 SQL 的模型,让它回头检查自己的输出,就像一个人写完代码自己 review,经常发现不了自己的盲区。论文里引用的一项调研明确指出,没有外部可靠反馈的自我纠正,几乎不会带来一致性的提升

Text-to-SQL修正的痛点:粗粒度经验复用为何频频翻车?

既然模型自省不靠谱,一个更自然的思路是:把历史上一对“错误 SQL → 确认正确的修正 SQL”收集起来,下次遇到类似问题时,就不用从零开始推理了,直接参考历史经验改就行。这种方法被称为经验式修正(experience-based correction),它把外部历史经验在推理阶段引入修正过程,不需要更新模型参数。
图片来源:论文 Figure 1
MIRA动机示意图
但问题来了。一次历史修正,往往同时修了好几个错误。就像图 1 里的这个例子:有一条历史修正,同时包含了三个修复点——A:要求客户必须存在订单(把 LEFT JOIN 改成 INNER JOIN);B:客户要去重(加 DISTINCT);C:只保留活跃客户(加 status='active' 过滤)。这三个修复被揉成了一个“完整经验包”。等到当前有一条新 SQL 出现时,它其实只犯了 B 这个去重的错,A 和 C 的修复对它完全不适用。但如果系统把整个经验包一股脑灌进去,就会把原本正确的 LEFT JOIN 改成 INNER JOIN、再加上一个状态过滤,导致一个本来没毛病的查询被改废。
这就是粗粒度经验复用的典型翻车场景。论文把这类问题总结为三个挑战:第一,一个历史修正可能混合了多个错误和修复,经验被“熔炼”成一个粗颗粒的知识单元后,就失去了独立复用的能力——这是记住什么(What to Remember)的问题;第二,经验触发条件定义在整个熔炼结果上,所以只要查询与历史案例“沾点边”,就把 A、B、C 这些不该同时用的修复全部激活了——这是何时激活(When to Activate)的问题;第三,一旦整个经验包被激活,历史修改就会被原样搬运到当前 SQL,根本不考虑两个案例在表结构、字段、写法上的差异——这是如何适配(How to Adapt)的问题。
要判断一条 SQL 修得对不对,论文里给了一个务实的标准:执行结果等价。也就是说,修正后的 SQL 只要执行结果和标准答案一致,就算修对了,不管它是不是和标准答案写得一模一样。这种评价方式跟 BIRD 等基准的官方评测是一致的:用户关心的是查出来的数据对不对,而不是 SQL 文本像不像标准答案。
执行结果等价定义公式
上面的公式中,Exec_D(·) 表示在数据库 D 上执行 SQL 并得到结果集,≡_exec 表示执行结果等价。公式说的是:修正后的查询 ṡ 与标准答案查询 s* 在数据库 D 上的执行结果必须等价。

MIRA核心机制:三步构建独立可复用的修复记忆项

为了解决上述三个挑战,论文提出了MIRA(Memory-Item Reuse and Adaptation,记忆项复用与适配)框架。MIRA 是一个可插拔的 SQL 修正器,核心思想可以概括为一句话:把历史修正拆成乐高积木式的独立修复记忆项,每个积木通过数据库证据验证后,再精准拼接到当前 SQL 上
图片来源:论文 Figure 2
MIRA整体框架图
MIRA 的总体流程分为离线(Ofline)在线(Online)两个阶段。离线阶段处理同一个数据库上积累的历史修正记录,构建一个固定的数据库级修复记忆库;在线阶段则面向当前新的查询任务,用修复记忆辅助修正。整个过程不更新任何模型参数,是纯粹的推理时增强。
在离线阶段,输入是一系列历史修正记录。论文用下面的公式来定义这些历史修正:
历史修正集合定义公式
其中 H_D 表示数据库 D 上可用的历史修正集合,包含 N 条记录;每一条历史修正 h_i 由三元组 (q_i, s_i⁻, s_i⁺)构成:q_i 是历史自然语言问题,s_i⁻ 是历史错误 SQL,s_i⁺ 是人工确认过的正确 SQL。所有修正记录都来自同一个数据库,共享相同的 schema 和数据实例。
MIRA 离线构建记忆库的过程包括三个关键步骤:修复恢复、修复单元识别、记忆项构建。
第一步是修复恢复(Repair Recovery)。注意,历史修正记录里的 s⁺(确认正确的 SQL)不一定是错误 SQL 的最小修复——可能顺手改了别名、调整了等价操作顺序,或者做了与纠错无关的重写。如果直接用 s⁻ 和 s⁺ 做文本 diff,得到的是“需求修复 + 无关改动”的混合物。所以 MIRA 采用“提出-执行-比较”的循环机制:修复模型从 s⁻ 出发,生成一个完整的候选 SQL;然后把这个候选 SQL 在数据库 D 上执行,将执行结果与 s⁺ 的执行结果比较。如果执行结果一致,这个候选 SQL 就被采纳为验证过的修复 SQL(validated repair SQL),记为 sᵥₐₗ。如果执行出错或者结果有差异,就把差异信息作为反馈传给下一轮。论文用下面的公式形式化了这个验证条件:
修复验证公式
sᵥₐₗ 只是用来识别修复单元,本身不会被存为记忆项。如果 s⁻ 本身无法执行、或者执行结果已经和 s⁺ 一致、或者在预算内找不到候选,这条历史修正就不会产生任何记忆项。
第二步是修复单元识别(Repair Unit Identification)。这一步要回答的核心问题是:一个历史修正到底包含几个“独立的可修复错误”?MIRA 先解析 s⁻ 和 sᵥₐₗ 的抽象语法树(AST),对两棵树做细粒度树差分,得到增、删、替换三类编辑操作。接着把在结构上相互依赖的操作归为一组。
分组之后如何才能确定它是一个独立修复单元?MIRA 的做法是:对每一组编辑操作 g,从 sᵥₐₗ 里只撤销这一组的修改、保留其他所有修改,得到一个新的 SQL,记为 s⁻ᵍ。然后把 s⁻ᵍ 和 sᵥₐₗ 的执行结果对比。一个组要“被接受”为修复单元,必须满足:历史问题要求的行为在 sᵥₐₗ 中得到了实现,而 s⁻ᵍ 与这个要求冲突。简言之,这个组确实修了某个必改的错误。如果只是改变了执行结果但与任务要求无关,比如换了一个等价写法,就不被接受。
图片来源:论文 Figure 3
修复记忆构建示意图
如图 3 所示,一个历史修正可能被拆成多个修复单元。比如“加上 DISTINCT”和“修正地区字段的字面量绑定”就是两个独立的修复单元。每个修复单元都针对一个独立的需求,并且在另一个修复存在的情况下被独立评估。
第三步是记忆项构建(Memory Item Construction)。一个被接受的修复单元还不能直接复用,必须把它转成结构化的记忆项。每个记忆项包含四个组成部分:
第一是语义契约,记录记忆项的适用条件、错误行为和期望行为、修复行为以及保留约束;第二是结构签名,记录编辑操作、受影响的子句和片段、引用的 schema 元素以及识别错误形式所需的最小上下文;第三是目标局部检查,指定需要在当前数据库上检查什么观测点、什么违规信号表示该错误在当前查询中再次出现;第四是来源支撑,保留历史需求、s⁻ 到 sᵥₐₗ 的比较以及用于判定该修复单元成立的事实。
值得一提的是,在线复用时只会用到前三部分,来源支撑只是作为溯源记录,不会被拿出来当模板照抄。

证据验证激活:如何确保记忆项在正确时机生效?

离线阶段把历史修正拆成了细粒度的记忆项,但记忆建好了,检索和激活又是另一回事。MIRA 在线阶段的第一个子步骤是记忆项检索(Memory Item Retrieval)
检索存在一个天然的“双通道”需求:相似需求可能通过不同的 SQL 写法实现,而相同的 SQL 错误结构也可能出现在不同的问题描述下。因此 MIRA 使用语义通道和结构通道并行检索:语义通道计算当前问题 q 与记忆项的适用条件、期望行为拼接后的 embedding 向量之间的余弦相似度;结构通道则解析当前 SQL,统计其 AST 派生关键字与记忆项结构签名的匹配个数。两个通道的排名按可用上下文预算合并去重,得到候选记忆项列表。
检索分数计算公式
公式中 Enc(q) 是问题 q 的 embedding 向量,arg(m) 和 req(m) 分别表示记忆项 m 的适用条件和所需行为,K(m) 表示记忆项的错误结构和最小上下文对应的关键字集合,K(s_cur) 是当前 SQL 的对应关键字集合。🔍
但检索只是“提醒”系统去检查候选记忆项,绝不等于激活。如果记忆项和当前任务“沾点边”就直接生效,就会重蹈粗粒度复用的覆辙。因此 MIRA 设计了核心的证据验证激活(Evidence-Verified Memory Activation)机制。一个记忆项要被激活,必须同时满足两个条件:第一,当前问题 q 确实需要该记忆项所记录的行为;第二,当前 SQL 中确实出现了该记忆项所记录的违规模式。
为了让“确实”这两个字落地,MIRA 在激活检查时把当前 SQL、数据库 schema 以及有界的数据观测交给求解器,自动检查当前 SQL 中已有的字符串谓词、标量变换等结构。如果还需要一条关键的数据库事实,求解器可以请求执行一次有界的只读探测查询,用真实数据来确认是否发生违规。见图 2 的在线阶段:m_j 被激活,因为它的需求和违规信号都得到了证实;m_k 被忽略,因为证据不支持。

目标局部适配:从历史修复到当前SQL的精准迁移

记忆项成功激活之后,下一步是把修复要求真正落到当前 SQL 上。这一步在 MIRA 中被称为目标局部适配(Target Local Adaptation)。历史案例和当前任务常常在上下文和 SQL 实现方式上存在差异,历史修复不能直接复制粘贴。如果照搬,就会出现图 1 里那种负迁移——把历史案例里“添加 INNER JOIN”和“加 status 过滤”的错误修改直接搬到一个只需要去重的查询上。
MIRA 的做法是:为每个激活的记忆项,把它的修复要求绑定到当前 SQL 中相关的表、列、值和位置;然后按照语义契约里记录的保留约束,确保当前 SQL 中已经正确的逻辑不被破坏;最后将多个激活的记忆项融合成一次完整的重写,而不是按历史修改逐条盲目套用。
在返回修正结果之前,MIRA 还会做一道机械验证关卡:候选 SQL 必须非空、与当前 SQL 不同、能解析为只读 SELECT/WITH 查询、能在数据库上成功执行,且至少返回一个输出列。如果候选 SQL 的执行结果和当前 SQL 相同,则视为无操作,不返回。任何一项不通过,MIRA 都保留当前 SQL 不做修改。
这个“宁可不动,不能改坏”的设计原则贯穿整个在线阶段——MIRA 对“回归”的防御是刻在机制里的,而不是靠调参。

实验结果解析:修复261个错误查询,仅回归18个的秘诀

MIRA 的评测覆盖两个主流跨域基准:BIRD 的 498 条已修正 Mini-Dev 集合和 ScienceBenchmark 的 299 条开发集,总共覆盖 14 个数据库。为了检验方法与上游生成器的解耦性,论文选了三个差异明显的 Text-to-SQL 上游系统:CHESS、DeepEye-SQL 和 OmniSQL-32B,组合出 6 个评测场景。每个数据库内约 25% 的查询用于构建历史信息(离线阶段),其余 75% 用于测试。每个 BIRD 场景包含 127 条训练查询和 371 条测试查询,每个 ScienceBenchmark 场景包含 75 条训练查询和 224 条测试查询,6 个场景合计 606 条训练查询、1785 条测试查询。所有修正方法在相同的数据切分和相同的当前 SQL 上运行,确保公平对比。
在修正模型选择上,MIRA 所有需要通用修正大模型参与的环节统一使用 gpt-5-2025-08-07;对比方法中的 SQLFixAgent 和 SHARE 保持其论文随附发布的专用本地模型不变。所有方法都只允许访问自然语言问题、基准提供的任务提示、数据库 schema 和数据实例、当前 SQL 以及各自方法允许的历史信息。标准答案 SQL 严格不进入任何修正提示。
对比方法也很有代表性:MAGIC(Memory-Augmented Generation with In-Context Correction?)— 即通过大模型把历史错误轨迹蒸馏成全局自修正指南的方法;TK-Boost 则是利用历史知识为当前推理提供知识增强。此外还有 SQLFixAgent 和 SHARE 两个专用修正模型。这几条基线分别代表了“粗粒度经验”“外部知识增强”和“专用修正模型”三条技术路线。
表格 1 是论文的核心实验结果——6 个评测场景下的执行准确率对比。
表1:各基准及上游Text-to-SQL系统上的执行准确率对比
可以看到,MIRA 在 BIRD 上平均提升执行准确率 16.53 个百分点,在 ScienceBenchmark 上提升 8.78 个百分点。更难得的是,1785 条测试查询中修复了 261 条错误 SQL,只造成 18 条原本正确的查询回归。这个修复/回归比在同类工作中属于相当出色的水平。
论文用下面这个公式来解释“净提升”:
净执行准确率变化公式
ΔEX 表示执行准确率的变化,M 是可评分查询总数,N_fix 是成功修复的错误查询数,N_reg 是被改坏的原本正确的查询数。这个公式直接说明:只看修复数没有意义,因为如果一边修好 10 条、一边改坏 10 条,净提升是 0。MIRA 的本质目标就是让 N_fix 尽量大、N_reg 尽量小。
图 4 直观展示了 MIRA 与各基线在“修复率-回归率”光谱上的位置。横轴是回归率(越低越好),纵轴是修复率(越高越好),越往右下角意味着性能越好。
图4:修复-回归权衡对比图
MIRA 落在右下角,修复率明显高于其他方法,回归率也压到了非常低的位置。图中虚线连起来的是净执行准确率增益相等的曲线。值得注意的是 TK-Boost 是论文作者根据其论文思路做了适配实现后的版本,这也是论文严谨性的体现——原版 TK-Boost 并不直接适配 SQL 修正任务。
图 5 对不同修复事件做了更精细的归因:大部分成功修复(225 条)只依赖单个记忆项,说明修复单元切分得足够干净;另外 36 条修复需要组合多个记忆项,证明多记忆项的组合能力也有实际需求。
图5:各评测场景中单一记忆项与多记忆项组合修复分布
论文还额外报告了两个方面的成本分析。
表2a:完整修正流程对比
(a)完整修正流程对比,展示了 MIRA 与其他修正方法在完整流程中调用大模型的次数和 token 消耗对比。
表2b:MIRA离线和在线使用成本对比
(b)离线和在线使用成本对比,将 MIRA 的两阶段耗时和 token 开销分别列出,便于评估整体运行代价。
为了验证三个核心设计各自的作用,论文在 BIRD-DeepEye 测试集上做了成对消融实验。
表3:BIRD-DeepEye测试集上的成对消融实验
消融结果验证了三件事:如果退化为粗粒度的完整案例复用(将整条历史修正直接作为记忆),回归数显著上升,证明“修复单元切分”是控制负迁移的关键;如果去掉证据验证激活、只凭语义或结构相似就触发记忆,回归率也明显抬升,说明单纯的相关性不能代替对错误是否真实发生的判断;如果去掉目标局部适配、直接照搬历史修改,修复率明显下降,因为历史写法和当前任务之间的差异无法被处理。三个模块缺一不可。

总结与展望:记忆增强SQL修正的未来方向

MIRA 这篇工作的核心价值,在于它对“SQL 修正中的经验复用”给出了一个更精细的操作框架:经验不应该以“整段修正案例”为单位来复用,而应该以“独立的修复单元”为单位,并且每次激活都必须经过证据验证。这种思路本质上把 SQL 修正从“找相似案例抄作业”变成了“定位错误、验证复发、精准修补”的流程化操作。
当然,MIRA 也有一些前提条件和局限性。它高度依赖同一数据库上积累的历史修正记录——如果某个数据库是全新的、没有任何历史修正,MIRA 的离线记忆库就是空的,在线阶段自然无法从中获得帮助。其次,证据验证激活需要访问真实数据库来执行探测查询,这在一些严格受限的生产环境里可能需要额外的权限控制。此外,修复恢复、语义判断和局部适配这些环节都要调用大模型,虽然离线阶段可以预计算,但在线推理的开销仍然存在。
展望未来,“把长期经验变成可增量维护的细粒度资产”这条路线,大概率会被更多系统采纳。MIRA 的智能之处在于:它不追求大而全的全局知识,而是老老实实地把每个修复单元做扎实。在 Text-to-SQL 修正这个精度需求极高的场景里,这种“少而准”的取向可能比“多而杂”更有工程价值。后续如果能支持跨数据库的修复记忆迁移,或者与训练式修正器结合,将进一步提升部署的灵活性和覆盖度。

龙迷三问

下面是龙哥对于大家可能的一些问题的解答:
这篇论文到底在解决什么问题?历史修正经验粗粒度复用常让SQL“修了A错又带出B错”。
这篇工作最值得看的点是什么?MIRA在BIRD上提升16.53个百分点,在ScienceBenchmark上提升8.78个百分点,共修复261个错误SQL,仅对18个正确SQL造成回归,在所有六个基准-上游系统组合中均取得最高或次高准确率。
这篇工作的边界或风险在哪里?优点:1)将历史修正分解为细粒度记忆项,避免粗粒度经验复用带来的负迁移;2)通过数据库证据验证激活,减少对正确SQL的误改;3)无需参数更新,可即插即用适配不同上游系统;4)在多个基准和上游系统上均取得显著提升。缺点:1)依赖GPT-5等强LLM,计算成本较高;2)离线记忆构建过程复杂,需要多轮生成-验证;3)在ScienceBenchmark-CHESS设置上不如MAGIC;4)对数据库证据的依赖可能在某些数据稀疏场景下受限。
如果你还有哪些想要了解的,欢迎在评论区留言或者讨论~

龙哥点评

论文创新性分数:★★★★☆

提出MIRA框架,将历史修正分解为独立可复用的修复记忆项,通过数据库证据验证激活并适配到当前SQL,实现无需参数更新的可靠SQL修正。

实验合理度:★★★★☆

执行准确率(Execution Accuracy, EX)、成功修复数(N_fix)、回归数(N_reg)、净变化(ΔEX)

学术研究价值:★★★★☆

提出MIRA框架,将历史修正分解为独立可复用的修复记忆项,通过数据库证据验证激活并适配到当前SQL,实现无需参数更新的可靠SQL修正;更关键的是问题定义是否可复用到同类任务。

稳定性:★★★☆☆

现有材料未提供充分的极端条件、重复运行或扰动测试,稳定性暂按中性评价。

适应性以及泛化能力:★★★☆☆

现有材料未完整展示跨数据集、跨场景或分布外实验,泛化能力仍需进一步验证。

硬件需求及成本:★★★☆☆

在线阶段平均每个输入约2.02次逻辑请求,消耗约6155输入tokens和1734输出tokens

复现难度:★★★☆☆

现有材料未确认完整代码、配置、数据处理脚本和权重是否齐备,复现难度暂按中性评价。

产品化成熟度:★★★☆☆

论文验证以研究实验为主,真实部署中的时延、成本、维护和异常场景仍需补充验证。

可能的问题:1)依赖GPT-5等强LLM,计算成本较高;2)离线记忆构建过程复杂,需要多轮生成-验证;

主要参考文献

[1] TK-Boost: 利用历史知识增强 Text-to-SQL 推理的方法。
[2] MAGIC: 将历史错误轨迹蒸馏为全局自修正指南的经验式修正方法。
[11] Jin et al. 提供的 BIRD Mini-Dev 已修正集合。
[16] DeepEye-SQL: 面向复杂数据库查询的 Text-to-SQL 系统。
[17] OmniSQL-32B: 基于 32B 大模型的 Text-to-SQL 生成系统。
[18] BIRD: 大规模跨域 Text-to-SQL 基准,含 12,751 条问题与 95 个数据库。
[25] CHESS: 一种面向真实数据库场景的 Text-to-SQL 智能体。
[31] Spider: 跨域 Text-to-SQL 标准基准数据集。

*本文仅代表个人理解及观点,不构成任何论文审核或者项目落地推荐意见,具体以相关组织评审结果为准。欢迎就论文内容交流探讨,理性发言哦~ 想了解更多原文细节的小伙伴,可以点击"阅读原文",查看更多原论文细节哦!       

转发文章 微博 X LinkedIn Facebook
龙哥读论文 · PaperDaily

本文基于龙哥读论文 PaperDaily 数据库整理,结合论文原文与工程视角进行解读。

LONGGE AI COMMUNITY

把每天读到的论文,变成长期积累

加入「龙哥读论文」知识星球,持续获取 AI 论文、资讯、开源项目、招聘与研究思路。

加入龙哥读论文微信群:添加微信 kangjinlonghelper,备注“研究方向 + 地点 + 学校/公司 + 昵称”。

龙哥读论文知识星球二维码 微信扫码加入知识星球