前言:索引就想一本书的目录页码,可以加速查询,表可以理解为就是一本书,索引就是目录,页码,索引还会影响到锁的应用,锁太乱了会影响到项目的并发。
MySQL语句的执行流程,
首先执行一个sql语句,通过连接层分配一个专用的连接线程,到sql层进行解析预处理,查看是否存在这个表以及有没有权限,对象存在性等检查,解析会生成AST的抽象语法树,优化:优化分为逻辑优化和物理优化。
逻辑优化主要是应用了一些算法,关系代数的等量转换(比如多表关联join的时候先进行where的语法下推这样会使得最后的结果集变小方便查询),
物理优化:物理优化会参考统计信息,表的统计信息主要是数据的分布(行数,重复值数量,估算结果等), 索引,主要是进行一些判断,优化器会自己判断你执行的语句是走索引好,还是走全表扫描好(索引的判断主要是来源于统计信息的判断和优化器的算法),物理优化的结果就是会产生执行计划,执行器按照执行计划去执行。
存储引擎,如果有索引,存储引擎会讲带有索引的数据页 返回给执行计划。
1,种类及查找算法演变以及mysql 支持的索引
BTREE : 99.9% ——> InnoDB ## 只要你是innodb的引擎,大多数都是 BTREE 索引支持的最大长度是3072字节
RTREE : no ——> MongoDB ## 空间索引,地理位置索引
HASH : MEM引擎 ——> Redis ## 哈希索引
FULLTEXT :TEXT类型 —-> ES ## 大字段,超过了65535个字节的
1000W user 查找 : 张三 ##
遍历
二分法 —-> 二叉树 —-> 红黑树 —-> Balance Ttree(平衡多叉树,简称为BTREE)
1.2BTREE查找算法演变
B-TREE : 普通 BTREE ##如果有主键,主键就是聚簇索引,如果没有主键,第一个唯一键而且不为空的就是聚簇索引,如果你没有主键和唯一键,就会生成一个隐藏的聚簇索引,只要你是innoDB的表,就会生成一个聚簇索引。
B+TREE : 叶子节点双向指针
B++TREE(BTREE): 枝节点的双向指针
1.3MySQL Btree 两类结构
Clustered : 聚簇(extent 区)索引
extent 区 : ##区的概念:连续的64(page)个数据页,默认是1M数据页,就是将 idb文件逻辑上格式化成一个一个的小方格,小方格里面存放的就是数据行。
IOT组织表 : 会按照聚簇索引组织方式,存储表中的数据,
Secondary : 辅助索引 分类,辅助索引也属于聚簇索引。
普通单列索引 ,普通联合索引 ,唯一索引 ,前缀索引 他们结构都不相同,但是底层都是用的BTREE索引
1.4聚簇索引的介绍:
1、 如果表中设置了主键(例如ID列),自动根据ID列生成聚簇索引
2、 如果没有设置主键,自动选择第一个NN唯一键的列作为聚簇索引
3、 自动生成隐藏(6字节row_id)的聚簇索引。
InnoDB表中一定是有聚簇索引。
建议: 在建表时,显示的创建主键,最好是数字自增列
1.5聚簇索引的优缺点:
优点:聚簇索引是连续的64个page页(数据页默认是1M) 也就是说保证了存储的数据都在连续的数据页当中,不用单独在进行排序,排序是非常消耗I/O资源的,可以很好的优化到 where,order by group by 这种查询
缺点: 聚簇索引只能优化到id列或者某一列,所以需要用到辅助索引。
1.5.1辅助索引介绍:
是一个占用空间的数据结构,包含主键的数据结构 ,辅助索引也存储在idb文件中
1.5.2辅助索引功能 :
1按照辅助索引列,作为查询条件时。
2. 查找辅助索引树,得到ID值
3. 拿着ID值回表(聚簇索引)查询
4.聚簇索引和辅助索引关系参考:
*辅助索引存的是什么?
辅助索引列值+ID主键值+指针
前提: 联合索引,先过滤最左列的数据拿到最左列的数据之后,在回表之前,将其他列的数据也过滤出来,如果查询的列里面存在没有索引的列,在进行回表,如果查询的列都有索引将不进行回表。
需要人为创建辅助索引,将经常作为查询条件的列创建辅助索引,起到加速查询的效果。
btree 构建过程
a. 叶子节点:提取主键(ID)+辅助索引列,按照辅助索引列进行从小到大排序后,生成叶子节点。(相邻的叶子结点,有双向指针)
b. 枝节点 :提取叶子节点辅助索引列的范围+指针,构建枝节点(相邻枝节点,有双向指针)
c. 根节点 :提取枝节点的辅助索引列的范围+指针,构建根节点
联合索引,最主要的原理就是最左原则,重复值少的那列在最左面,过滤的时候必须包括最
左列,最左列包括了根节点和叶子节点,如果没有最左列将无法使用辅助索引
1.5 使用索引考虑的事项
回表是什么? 回表会带来什么问题? 怎么减少回表?
a. 按照辅助索引列,作为查询条件时,先查找辅助索引树得到ID,再到聚簇索引树查找数据行的过程。
b. IO量多、IO次数多、随机IO会增多、SQL层和engine交互多次。IO偏高 ,CPU 偏高。
c. 减少回表建议:
1. 辅助索引能够完全覆盖查询结果,可以使用联合索引。
2. 尽量让查询条件精细化,尽量使用唯一值多的列作为查询条件
3. 优化器:MRR(Multi-Range-Read),ICP(index condition pushdown) ,锦
上添花的功能。
mysql> select @@optimizer_switch;
mysql> set global optimizer_switch=’mrr=on’;
功能:
1. 辅助索引查找后得到ID值,进行自动排序
2. 一次性回表,很有可能受到B+TREE中的双向指针的优化查找。
