假设 :一个数据页IO成本就是1.0,一条数据检 测的CPU成本就是0.2

找到可用的索引

select * from t where x1=xx and x2=xx 此时你有两个索引,分别是针对x1和x2建立的,就会先看看这个SQL可以用到哪几个索引,此时发现x1和x2的索引都能用到,他们俩索引就是possible keys。

计算全表扫描的成本

核心:数据页的数量 和rows记录数
show table status like “表名” 统计信息中,rows(估算的值)和data_length两个信息
data_length:是表的聚簇索引的字节数大小(主键索引),单位b
数据页的数量 = data_length/1024/16;
data_length/1024 单位换算成kb
data_length/1024/16 一个数据页 大小为16kb

IO成本就是:数据页数量 1.0 + 微调值;使用多少个数据页
CPU成本就是:行记录数
0.2 + 微调值;每一条数据都判断是否符合搜索条件

比如你有数据页100个,记录数有2万条
全表扫描的成本 = IO成本 + CPU成本 = 1001.0 +200000.2 = 4100

普通索引成本

一般都是两步走,先从二级索引查询一波数据,再根据这波数据 的主键去聚簇索引回表查询
二级索引的成本:
IO:查询条件涉及到几个范围(数据页)1或者是n,基本就是个位数这个级别
CPU:每条数据判断是否符合条件 数据条数0.2
回表成本:
IO:一条数据估算成本为一个数据页,
CPU:每条数据判断是否符合条件 数据条数
0.2
假如 二级索引扫描到 100条数据
成本 = (1+1000.2)+(100+1000.2)=141

多表关联查询成本

从驱动表开始计算成本,再计算关联表的成本,都是使用单表的计算方式

成本优化

1.常量替换
i = 5 and j > i就会改写为i = 5 and j > 5
x = y and y = k and k = 3会给你优化成 x = 3 and y = 3 and k = 3
b = b and a = a 一看就是没意义的,就直接 给你删了
这个比较有意思的替换
select from t1 join t2 on t1.x1=t2.x1 and t1.id=1
select
from t1 join t2 on t2.x1=常量a
常量a是t1.id=1那条记录的 x1字段的值
2.子查询优化
执行顺序的优化
子查询转换为联合查询 (semi join 半连接)