85 | 提纲挈领的告诉你,SQL语句的执行计划和性能优化有什么关系

执行计划:
提交一个sql给mysql,他内核里的查询优化器,会针对mysql的语义生成一个执行计划
这个执行计划代表了,如何筛选过滤,如何分组,如何使用函数,如何排序,可以调优索引

86 | 以MySQL单表查询来举例,看看执行计划包含哪些内容(1)

1、const
userId 是主键
1)select from users where userId = ‘2’;
2)根据索引直接可以快速查找数据的过程,是const,性能超高常量级的
3)要点:二级索引必须是唯一索引
2、ref
userName 建立一个普通索引
1)select
from users where userName = ‘王二’;
2)必须是从索引最左侧开始,连续多个列都是等值比较才是ref(数据量大的情况)
3、ref or null
1)select * from users where userName = ‘王二’ or userName is null ;
2)如果用了 is Null 这种语法,即使name 是主键或唯一索引,还是只能走 ref
3)如果是针对一个二级索引,比较了一个值且限定了 is null 则叫 ret or null

87 | 以MySQL单表查询来举例,看看执行计划包含哪些内容(2)

1、range
age 建立一个普通索引
1)select * from users where age <20 and age > 10
2)进行范围筛选,这种方式就是range
2、index
userName 和 city 做一个普通联合索引
1)select userName,city from users where city = ‘北京’
2)针对这种只要遍历二级索引,就可以拿到想要的数据,不需要回源到聚簇索引的访问方式,为index
image.png
3、all
全表扫描

88 | 再次重温写出各种SQL语句的时候,会用什么执行计划?(1)

89 | 再次重温写出各种SQL语句的时候,会用什么执行计划?(2)

select * from table where x1 = xx and x2 = xx
x1、x2分别都有一个索引
有可能让查询优化器生成一个执行计划,对x1字段的索引树进行查找,查出一波数据,然后对x2索引树查出一波数据,两波数据,按照主键做一个交集

90 | 再次重温写出各种SQL语句的时候,会用什么执行计划?(3)


91 | 深入探索多表关联的SQL语句到底是如何执行的?(1)

select * from t1,t2
where
t1.x1= xx
and t1.x2 = t2.x2
and t2.x3 = xxx
1)首先根据 t1.x1 从t1表查出来一批数据(假设是2条),可能是 const\ref\index等(根据索引建立不同)
2)对1)中的2条数据,根据每条数据的 x2值和 t2.x3 =xxx条件,去t2表里去匹配数据
3)t1表是驱动表,t2是被驱动表

92 | 深入探索多表关联的SQL语句到底是如何执行的?(2)

内联 外联

93 | 深入探索多表关联的SQL语句到底是如何执行的?(3)
嵌套查询


94 | MySQL是如何根据成本优化选择执行计划的?(上)

1)IO 成本:从磁盘读数据到内存,读一页的成本约定为1.0
2)CPU成本:拿到数据,对数据做一些运算,验证是否符合搜索条件、排序分组等,一条数据的成本约定为0.2
3)show table status like ‘表名’
4)rows 表里的记录数、data_length 表的聚簇索引的字节数大小(单位kb) ,除以16 kb(默认一页大小),就是有多少页
image.png
5)IO成本 = 数据页量1.0 +微调值
6)cpu成本 = 行记录数
0.2 + 微调值

95 | MySQL是如何根据成本优化选择执行计划的?(中)

索引成本
1)根据二级索引查询,IO成本:11.0 =1 (或 n 1.0 = n ),基本上是个位数级别
2)二级索引查询如果是100条数据,CPU成为:1000.2 = 20
3)拿到100条数据,到聚簇索引去查完整数据,假设一条数据在一个数据页,那就是100个数据页,IO成本:100
1.0 = 100
4)cpu成本:100 * 0.2 = 20
5)总成本 = 1+20+ 100+ 20

96 | MySQL是如何根据成本优化选择执行计划的?(下)

表连接成本

97 | MySQL是如何基于各种规则去优化执行计划的?(上)
1)mysql会把无关紧要的括号删掉
2)i = 5 and j > i 这样的会替换成 i = 5 and j>5

100 | 透彻研究通过explain命令得到的SQL执行计划(1)
1、explain 命令
1)explain select * from users where userId = ‘1’;
image.png
2)ID : 每个select 都对应一个id ,复杂sql可能有多个select,一个select一个id
3)select_type : 一条执行计划对应的查询是个什么类型的查询
4)table : 表名
5)partitions : 表分区
6)type : 表的访问方法 : const\all\ref\range\index
7)possible_keys : 跟type结合起来的,type确定访问方式了,possible_key 就是实际选择的那个索引
8)key_len :索引的长度

103 | 透彻研究通过explain命令得到的SQL执行计划(4)
select_type
1)单表查询或者多表连接查询,都是 SIMPLE
2)union语句
image.png