本系列前几篇都在优化器的执行轴上打转:查询改写(只让 LLM 改 SQL 几乎什么都不会发生、规则改写在 DSB 上的盲区)、计划调优(把 LLM 当 plan-tuner 而不是 optimizer)、物理设计(当索引调优器的成本模型说谎时)。这一篇往下捅到优化器最底层的那个输入——基数估计(cardinality estimation,CardEst)。
来源是北京大学和字节跳动团队 2026 年 3 月底放出的一篇实证研究(arXiv:2603.28080),标题是一个很老实的问句:Can Large Language Models be a Cardinality Estimator? An Empirical Study。它不预设答案,而是把 Llama-3 8B 拽进 PostgreSQL 的优化器里,认认真真量了一遍精度和端到端两笔账。
结论分两半,而且这两半合起来才是这篇值得读的地方:精度上 LLM 赢得很干净,端到端上它一度输得很难看。
基数估计为什么是优化器的命门
优化器选执行计划,靠的是成本模型;成本模型算得准不准,几乎全压在基数估计上——每个子查询(尤其是多表 join 之后)到底会吐出多少行。估多了,优化器以为该走 hash join 建大表;估少了,它以为几行数据随便嵌套循环。一个基数估错一个数量级,下游的 join order、join 算法、并行度可能全跟着错,计划直接劣化。
传统估计器要么靠直方图加独立性假设(PostgreSQL 默认那一套),要么靠学习型模型(MSCN、DeepDB、NeuroCard、以及较新的 PRICE)。它们的共同难题是多表关联下的相关性:join 越多,数据分布越扭曲,估得越离谱。这正是这篇论文想看 LLM 能不能啃下来的地方。
证据一:精度,LLM 是真赢
方法上,团队没有把表结构硬塞进某个 MLP 编码器——他们试过,严重过拟合。最终方案是三件套:精心设计的 prompt(喂进粗粒度统计量,还把 PRICE 等其他估计器的输出也塞进上下文)、LoRA 微调(关键是让模型逐位生成数字 token,而不是回归一个标量)、以及推理时的 self-correction 迭代。默认模型是 Llama-3 8B,底层引擎 PostgreSQL,用 PilotScope 把估出来的基数注入回优化器。
精度用 Q-error 衡量(估计值与真实值之比取较大方向,1 是完美)。一个最能说明问题的设定:训练时只用 join 数小于 3 的查询,测试时全考 join 数大于 3 的查询——也就是逼模型外推到更复杂的关联上。99 分位 Q-error 这一栏:
| 估计器 | 99 分位 Q-error |
|---|---|
| PostgreSQL | 52594 |
| MSCN | 17239 |
| DeepDB | 20236 |
| PRICE(最佳 baseline) | 10672 |
| Llama-3 + 微调 | 2581.73 |
差距不是几个百分点,是数量级上的尾部收紧。这张 IMDB 表里,99 分位从 PRICE 的 10672.53 收到 2581.73,降幅 75.81%。换到 STATS 的标准设定上,99 分位相对最佳 baseline 最高降 74.1%。跨 IMDB、STATS、ErgastF1、Genome 几个负载,LLM 在几乎所有设定上都压过最强 baseline PRICE。尾部估得准,意味着最容易把优化器带沟里的那批查询被救回来了。
到这里,如果文章停笔,它就是又一篇"LLM 又赢了"的稿子。但作者接着量了端到端。
证据二:端到端,一度倒亏
把更准的基数喂回优化器,计划应该更好,查询应该更快——这是直觉。实测却在好几个负载上翻了车。
在 JOB-light、ErgastF1 上,纯 Llama+PFT 的端到端总时间反而超过了最强 baseline PRICE:它估得更准,单看查询执行时间也把 PG、PRICE、ASM 大幅压过,但每估一次都要做一次 8B 模型的推理,这笔延迟累计进总账,在这两个负载上吃光了精度带来的计划收益。“更准"在这里第一次跟"更快"脱钩了。
这是全文的命门,也是 perf 视角里最该被记住的一句:**基数估得准是收益,估一次的代价是成本,端到端是两者相减。**单看精度榜,LLM 全胜;算上每次推理的 wall-clock,账立刻就不一样了。
当然不是处处倒亏。在 STATS、Genome 这类更复杂、计划空间更大的负载上,精度优势带来的计划改进远超那点推理开销,端到端依然净赚。问题从"LLM 行不行"变成了"什么时候值得调 LLM”。
证据三:cost-aware 门控,一个很老的智慧
作者的解法不在模型里,在调度上,而且是个查询引擎的人一眼就认得的老办法:用成本模型当看门人。
具体做法(论文里叫 LLMs+PFT+cost):对每个子查询,先用 PostgreSQL 自己的成本模型估一下它的执行成本;成本超过阈值的高成本子查询,才花钱调 LLM 去精修基数;成本很低的子查询,直接用 PostgreSQL 原生估计就够了。阈值则是从"估计成本 vs 实际运行时间"的经验关系里标定出来的。
道理很顺:高成本子查询往往 join 多、相关性强,恰恰是 baseline 精度退化最严重、而 LLM 优势最大的地方——这里花一次推理,换回一个不至于劣化数倍的计划,划算;低成本子查询 baseline 本来就估得够准,再调 LLM 纯属浪费那笔延迟。门控把昂贵的算力精确地花在它能改变结局的子查询上。
这跟本系列一以贯之的主轴是同一句话:**LLM 不取代优化器,而是被优化器的纪律约束着用。**上一篇里成本模型是被 LLM 补盲的对象,这一篇里它反过来成了约束 LLM 的闸门——成本模型两头都在。
证据四:把开销账摊开看
值得把成本这一侧也说清楚,免得只记住精度。
- 预微调(PFT):一次性离线,约 12 小时,但产物可复用到任意数据库实例,摊销下来不贵。
- 目标库微调:LoRA,约 50–60 分钟,跟多数 baseline 相当,甚至比 DeepDB、FactorJoin、ALECE 还短。
- 单次推理延迟:这是结构性短板,也是证据二里端到端倒亏的根源,门控就是为它而设。
- self-correction:迭代纠偏减少幻觉,但作者实测 IMDB 上 85.03% 的查询零迭代就够准,只有 9.24% 需要最多 5 轮——大头并不真的迭代,开销没有想象中夸张。
硬件是 8 张 A-800(80GB)、512GB 内存,用 LLaMA-Factory 训。代码开源(PKU-SDS-lab/EA-LLM-IN-DB)。规模不小,但训练侧的账基本能摊平,真正卡脖子的始终是推理那一下。
收束:成本模型当看门人
把四块证据连起来,这篇论文其实回答了标题那个问句,但答案带个限定:大模型能当基数估计器,前提是你别每个子查询都去叫它。
精度它确实赢了,而且是在最难的多 join 尾部赢的;但把推理延迟摊进端到端,无脑全调就会倒亏。真正的工程贡献不是那个微调好的 Llama,是那个朴素的门控——让优化器自己的成本模型决定哪些子查询配得上一次 LLM 推理。贵重的算力花在刀刃上,这不是 CardEst 一家的事,它大概率是 LLM 进查询引擎各个环节的通用范式:模型负责在难的地方更准,成本模型负责把它约束在划算的地方调用。
下一个该被这样审视的,是优化器里还有哪个环节,既受得住 LLM 的精度红利,又扛得起每次调用的延迟账。
来源
- arXiv:2603.28080 — Can Large Language Models be a Cardinality Estimator? An Empirical Study,北京大学 + 字节跳动 + UPenn,2026-03-31。
- 代码:https://github.com/PKU-SDS-lab/EA-LLM-IN-DB
- 访问日期:2026-05-31。