Navicat 17 不计算 Cost 值,仅原样展示数据库返回的 COST 字段;MySQL 与 Oracle 的 Cost 定义、单位及计算逻辑互不兼容,且 Navicat 不暴露统计上下文或明细,导致该值缺乏可解释性。

Navicat 17 显示的 Cost 值根本不是它自己算的
Navicat 17 从不参与 Cost 计算,它只是把数据库返回的 COST 字段原样展示在执行计划表格里。你看到的数字,完全来自 MySQL 8.0+ 的优化器估算,或 Oracle 的 PLAN_TABLE.COST 列——Navicat 没有内置公式、不读取 innodb_page_size 或 ioseektim 参数,也不调用任何成本模型函数。
MySQL 和 Oracle 的 Cost 逻辑本身就不兼容
MySQL 的 COST 是归一化相对值,由 read_cost + eval_cost + sort_cost 等加总而来,依赖 ANALYZE TABLE 更新的 CARDINALITY;Oracle 的 COST 则基于物理参数公式:(#SRds * sreadtim + #MRds * mreadtim + CPUCycles / cpuspeed) / sreadtim,需要 V$SYSTEM_PARAMETER 中的真实系统统计值。两者单位、量纲、前提完全不同,强行横向比较毫无意义。
Navicat 不暴露底层统计上下文,导致 Cost 失去可解释性
真正影响 Cost 判断的,是 Navicat 界面里根本看不到的东西:
- MySQL 的
rows估算严重依赖information_schema.STATISTICS,若表长期未ANALYZE TABLE,Cost 就是拍脑袋值 - Oracle 的
COST若缺失直方图,effective_index_selectivity会严重失真,但 Navicat 不提示“统计信息陈旧” - MySQL 的
EXPLAIN FORMAT=JSON能展开cost_info细节,而 Navicat 默认只显示汇总列,不提供展开按钮或明细视图
所谓“不同”,其实是误把展示当计算
很多人以为 Navicat 17 升级后 Cost 算法变了,其实只是它开始支持更多数据库(如 PostgreSQL 的 EXPLAIN ANALYZE 输出),而不同数据库的 Cost 定义天然冲突。比如 PostgreSQL 根本不输出 COST 列,它用的是 total_cost 和 startup_cost,Navicat 把它硬映射到同一列名下,看起来就像“数值不准”。真正的卡点永远在数据库侧:没收集统计信息、用了函数导致索引失效、绑定变量窥探未生效——这些,Navicat 连提醒都不会给你。


















