美文网首页
MySQL - 索引优化技巧

MySQL - 索引优化技巧

作者: kyo1992 | 来源:发表于2021-04-15 09:08 被阅读0次

前言

本文介绍几种最常用的几种索引优化手段

  • 联合索引;
  • 最左前缀原则;
  • 调整索引列顺序;
  • 索引覆盖;
  • 普通索引和唯一索引选择。

联合索引

在建立索引的时候,尽量在多个单列索引上判断下是否可以使用联合索引,联合索引使用不仅可以节省空间,还可以更容易的使用到索引覆盖。

索引的字段越多,更容易满足查询需要返回的数据。 例如联合索引(a_b_c),等价于有了三个索引:a,a_b,a_b_c,索引树的叶节点数据没变,索引data字段数据是省数据了。

创建原则

在创建联合索引的时候,应该把频繁使用的列,区分度高的列放在前面,区分度高代表筛选粒度大,也可以在常需要作为查询返回的字段上增加到联合索引中,如果在联合索引上增加一个字段而使用到了覆盖索引(索引下推),避免回表,就建议使用联合索引。

使用场景
  • 考虑当前是否已经存在多个可以合并的单列索引,如果有,将当前多个单列索引创建为一个联合索引。
  • 当前索引存在频繁使用作为返回字段的列,可以考虑当前列是否可以加入到当前已经存在的索引上,使其查询语句可以使用到覆盖索引。

最左前缀原则

最左前缀原则和联合索引的索引存储结构和检索方式有关。


联合索引底层存储结构

如上图,在联合索引树上,最底层的叶子节点按照第一列name从左到右递增排列,但是age和position是无序的,age只有在name值相等的情况下,小范围内递增有序,而position列只有在name和age两列相等的情况下小范围内递增有序。

select * from abc_innodb where name = 'haha' and age = 30 and position = 'dev';

像这个查询,B+树会比较name列来确定下一步搜索方向,往左还是右,如果name列相同再比较age列。如果查询条件没有name列,B+树就不知道第一步应该从哪个节点查起。

select * from abc_innodb where name  like 'Bi';

如果你要查的是所有名字以'Bi'为前缀的人,也能够用上这个索引,查找到第一个符合条件的记录,然后向后遍历,直到不满足条件为止。

所以,不只是索引的全部定义,只要满足最左前缀,就可以利用索引来加速检索。这个最左前缀可以是联合索引的最左 N 个字段,也可以是字符串索引的最左 M 个字符。

例如对于BLOG、TEXT和VARCHAR类型的列,必须使用前缀索引,只索引开始的部分字符。

调整索引列顺序

基于上面对最左前缀索引的说明,讨论一个问题:在建立联合索引的时候,如何安排索引内的字段顺序。

评估标准是,索引的复用能力。因为可以支持最左前缀,所以当已经有了 (a,b) 这个联合索引后,一般就不需要单独在 a 上建立索引了。因此,第一原则是,如果通过调整顺序,可以少维护一个索引,那么这个顺序往往就是需要优先考虑采用的。

要为高频请求创建 (身份证号,姓名)这个联合索引,并用这个索引支持“根据身份证号查询地址”的需求。

那么,如果既有联合查询,又有基于 a、b 各自的查询呢?查询条件里面只有 b 的语句,是无法使用 (a,b) 这个联合索引的,这时候不得不维护另外一个索引,也就是说需要同时维护 (a,b)、(b) 这两个索引。

覆盖索引

定义:索引包含所有需要查询的字段的值,避免回表。
覆盖索引是一种很常用的优化手段。因为在使用辅助索引的时候,我们只可以拿到主键值,相当于获取数据还需要再根据主键查询主键索引再获取到数据。

但是试想下这么一种情况,在上面abc_innodb表中的组合索引查询时,如果我只需要abc字段的,那是不是意味着我们查询到组合索引的叶子节点就可以直接返回了,而不需要回表。这种情况就是覆盖索引。

普通索引和唯一索引选择

查询过程区别

对于普通索引来说,查找到满足条件的第一个记录 (5,500) 后,需要查找下一个记录,直到碰到第一个不满足 k=5 条件的记录。

对于唯一索引来说,由于索引定义了唯一性,查找到第一个满足条件的记录后,就会停止继续检索。

两者性能区别微乎其微。
因为InnoDB 的数据是按数据页为单位来读写的。也就是说,当需要读一条记录的时候,并不是将这个记录本身从磁盘读出来,而是以页为单位,将其整体读入内存。在 InnoDB 中,每个数据页的大小默认是 16KB。 即使普通索引需要继续往后查找,能在同一页内停止搜索概率还是很大的。

更新过程区别

当更新操作涉及唯一索引时,因为唯一性约束,当数据不在内存页时,不能使用change buffer直接更新,必须将数据从磁盘中加载。 而普通索引则没有这个限制。
所以,这两类索引在查询能力上是没差别的,主要考虑的是对更新性能的影响。所以,尽量选择普通索引。

相关文章

  • MySQL索引知多少

    mysql索引 总结关于mysql的索引,查询优化,SQL技巧等 1 索引类型 B-Tree索引 Hash索引 ...

  • mysql 索引优化

    索引的存储分类 索引的创建与删除 索引查看 mysql常用语句优化技巧定期优化表 常用优化 2.应尽量避免在whe...

  • MySQL - 索引优化技巧

    联合索引 在建立索引的时候,尽量在多个单列索引上判断下是否可以使用联合索引,联合索引使用不仅可以节省空间,还可以更...

  • 浅谈对数据库索引和主键的理解

    1、什么是索引? 面试时候,常常被问到自己熟知的Mysql优化技巧,索引一定会被提及。那么,什么是索引呢?索引是一...

  • 10分钟掌握数据类型、索引、查询的MySQL优化技巧

    10分钟掌握数据类型、索引、查询的MySQL优化技巧? 不存在的! 本文的内容是总结一些MySQL的常见使用技巧,...

  • mysql 查询优化

    参考文章:mysql 如何优化left joinmysql 创建索引和删除索引mysql 查看索引 查看字符编码

  • MySQL(4)应用优化

    MySQL应用优化 4.1-MySQL索引优化与设计 索引的作用 快速定位要查找的数据 数据库索引查找 全表扫描 ...

  • Mysql 相关

    MySQL索引 MySQL索引背后的数据结构及算法原理 覆盖索引和回表操作 MySQL性能优化 MySql表分区详...

  • MySQL,必须掌握的6个知识点

    目录 一、索引B+ Tree 原理 MySQL 索引 索引优化 索引的优点 索引的使用条件 二、查询性能优化使用 ...

  • MySQL相关文章索引(2)

    1.MySQL性能优化 对MySQL语句的性能分析与优化 Mysql 监控 Innodb 阻塞状况 MySQL索引...

网友评论

      本文标题:MySQL - 索引优化技巧

      本文链接:https://www.haomeiwen.com/subject/zdbikltx.html