索引
索引就类似于字典的目录,有了目录就可以很快地查询到一个字。没有目录,你只能一个一个地去查。
InnoDB的索引模型
Mysql的默认引擎是InnoDB,InnoDB的数据是根据主键顺序以索引的形式存放的,这种称为索引组织表。InnoDB的索引模型是B+tree,所有数据都是存储在B+ tree中。
每一个索引都有一个对应的B+ tree。
InnoDB为什么要使用B+tree做为索引结构,因为b+tree更矮更胖,可以减少访问磁盘的数量,提高查询速度。
索引
- 主键索引:主键索引中叶子节点存放的数据是整行数据(又称聚簇索引)
- 非主键索引:非主键索引中叶子节点存放的是主键索引的值(又称二级索引)
区别
主键索引和非主键索引查询的区别在于,非主键索引中叶子节点存放的是主键索引的值,所以得找到主键索引后,根据主键索引去找行数据,这个过程被称为回表。所以直接使用主键索引查询会比非主键索引更快些。
索引维护
为了维护B+tree的有序性,在向表中插入或删除新数据的时候,需要做必要的维护。如果数据超过了一定大小,则需要做拆分或者合并处理。这两个操作下,性能会受影响。所以在考虑维护的情况下,我们在选择自增主键或者指定唯一字段做主键时,需要考虑占用的内存大小。
覆盖索引
当查询条件为非主键索引,而查询字段只有主键时,则不需要进行回表,因为非主键索引的叶子节点存储的值就是主键,称为覆盖索引。覆盖索引减少了树查询的次数,可以显著地提高查询效率,因此是非常重要的优化手段。
覆盖索引的使用场景:
- 当需要根据非主键索引查询另一个非主键字段的场景高发时,则可以建立复合索引,可以达到覆盖索引的效果。(需要分析维护索引消耗的时间和树查询的节约的时间)
最左前缀原则
B+tree通过最左前缀来定位记录。最左前缀不只是整个索引的定义,只要开头满足了最左前缀,索引就能生效。比如 name like “张%”, (name, age) 是联合索引,则这个模糊查询是可以用上索引的。
索引下推
(name, age)是联合索引,这时候需要查询一个10岁的姓张的男孩。
sql 为 select * from user where name like ‘张%’ and age = 10 and is_male = 1
根据最左前缀原则,可以分析出name是走了索引(name, age)。而之后的分析。
在MySQL索引5.6之前,只能获取到姓张的数据的主键id,再一个个回表比对。
MySQL5.6引入了索引下推优化。在树搜索找到了所有姓张的数据,再去过滤掉age != 10的数据,剩下的数据再去回表查询。
索引下推可以减少回表次数,提高查询效率