MySQL索引优化总结

本文涉及的产品
RDS AI 助手,专业版
RDS MySQL DuckDB 分析主实例,集群系列 4核8GB
RDS MySQL DuckDB 分析主实例,基础系列 4核8GB
简介: 本文主要对常见索引失效的情况进行总结,并提出相关优化建议;另外,还介绍查询优化分析方法和思路,以及OrderBy关键字排序优化和group by分组优化方法和优化策略
  1. 索引失效总结(复合索引)
  • 单表查询时,保证where查询条件的顺序和个数与索引建立的顺序和个数要保持一致
  • 最佳左前缀法则,即where的查询条件要从索引的列的最左列开始并且不跳过索引中的列
  • 不在索引列上做任何操作(计算、函数、(自动or手动)类型转换),会导致索引失效而转向全表扫描。
  • 存储引擎不能使用索引中范围条件右边的列,即where 范围查询条件后面的索引列失效
  • 尽量使用覆盖索引(只访问索引的查询(索引列和查询列一致)),减少select*查询
  • 查询条件中使用is null,is not null也无法使用索引
  • like以通配符开头('%abc.... ')mysql索引失效会变成全表扫描的操作,只有写在最右边才会避免查询失效;2. 在生产过程中,必须要写两边百分号

对于 like 两边百分号的原因,比较推荐的方法是使用覆盖索引

  • 字符串不加单引号索引失效
  • 少用or,用它来连接时会索引失效
  • mysql在使用不等于(!=或者<>)的时候无法使用索引,会导致全表扫描


  1. 一般性建议
  • 对于单键索引,尽量选择针对当前query过滤性更好的索引
  • 在选择组合索引的时候,当前Query中过滤性最好的字段在索引字段顺序中,位置越靠前越好。
  • 在选择组合索引的时候,尽量选择可以能够包含当前query中的where字句中更多字段的索引
  • 尽可能通过分析统计信息和调整query的写法来达到选择合适索引的目的
  • 使用索引可加快数据检索速度,但为每个列都建立索引没有必要。因为索引自身也需要维护,并占用一定的资源,可以按照以下标准选择建立索引的列
  • 频繁搜索、查询选择的列
  • 经常排序、分组的列
  • 经常用于连接的列(主键、外键)

在MySQL可以通过查询当前会话的last_query_cost的值来得到其计算当前查询的成本


  1. 索引优化总结
  • 单列索引还是多列索引?

由于mysql只能用到你所有建立的索引中的唯一一个最优索引,所以如果建立多个单列索引,其实效率并不会高(虽然  mysql5.x以上的版本,会在查询时,做索引合并的优化,但仍不建议这么做)

  • 索引可以优化查询,那么索引真的越多越好吗?

由于mysql的索引是表的数据的一部分,就像你手中的汉语词典一样,目录越庞大,可读性越差(查询性能越差)。而且,在insert,update,delete时,都要额外维护索引的成本,建立过多的索引可能意味着更差的写性能。

  • 如何优化查询?
  • 尽可能的让查询走索引,查询条件尽量避免出现 or  
  • 范围查询, col like '%xxx%'模糊查询,会导致范围|模糊查询 之后的条件索引失效
  • 子查询使用关联查询替代
  • 关联查询,用小表驱动大表
  • 学会使用limit,limit会让你的查询提前返回需要的行,这点在排序的时候尤其有用(避免全部排序,只排序需要的列)
  • 在多租户的系统里,千万别漏掉tenant_id这个辨识度最高的列(tenant_id建议放在最左边)


  1. 查询优化分析
  • 观察,至少跑1天,看看生产的慢SQL情况。
  • 开启慢查询日志,设置阈值,比如超过5秒钟的就是慢SQL,并将它抓取出来。
  • explain+慢SQL分析

Explain能够告诉你这个查询在数据库中是一个什么样的执行计划来实现的。首先我们需要有个目标,通过不断调整尝试,再借助Explain来验证结果是否满足自己的需求,直到得到预期的结果。

  • show profile分析

MySQL的Explain执行计划可以用来对Sql语句进行分析,是否进行全表扫描,是否用了索引,或者是sql语句先后执行计划,有没有用临时表等等,由此来进行Sql优化,而show Profile和Explain一样都是用来查看Sql语句分析的,但是形式不一样,show Profile用来分析当前会话语句执行的资源消耗情况,能清晰的知道sql执行过程,以及过程中消耗的时间。

  • 进行SQL数据库服务器的参数调优。


  1. 查询优化原则
  • 小表驱动大表,即小的数据集驱动大的数据集


  1. 查询优化思路
  • 优化更需要优化的查询
  • 定位优化对象的性能瓶颈
  • 明确优化的目标
  • 从Explain入手
  • 多使用 profile
  • 永远用小结果集驱动大结果集
  • 尽可能在索引中完成排序
  • 只取出自己需要的字段(Columns)
  • 仅仅使用最有效的过滤条件
  • 尽可能避免复杂的join


  1. OrderBy关键字排序优化

order by 子句,尽量使用index方式排序,避免使用file sort方式排序,尽可能在索引列上完成排序操作,遵照索引键的最佳左前缀法则。


会产生index方式排序:

  • 排序字段使用索引列:ORDER BY 语句使用索引最左前列
  • 使用Where子句与Order By子句条件列组合满足索引最左前列;


排序字段不在索引列:mysql就要启动双路排序和单路排序

优化策略:

  • 增大sort_buffer_size参数的设置
  • 增大max_length_for_sort_data参数的设置


提高 Order By的速度:

  • Order by时 select*是一个大忌只 Query需要的字段,这点非常重要。在这里的影响是:
  • 当 Query的字段大小总和小于max_length_for_sort_data而且排序字段不是TEXT|BLOB类型时,会用改进后的算法——单路排序,否则用老算法一一多路排序。
  • 两种算法的数据都有可能超出 sort buffer的容量,超出之后,会创建tmp文件进行合并排序,导致多次O,但是用单路排序算法的风险会更大一些所以要提高sort_buffer_size。
  • 尝试提高 sort_buffer_ size

不管用哪种算法,提髙这个参数都会提高效率,当然,要根据系统的能力去提高,因为这个参数是针对每个进程的

  • 尝试提高max_length_for_sort_data

提高这个参数,会增加用改进算法的概率。但是如果设的太高,数据总容量超出 sort_buffer_size的概率就增大,明显症状是高的磁盘ⅣO活动和低的处理器使用率


  1. group By关键字排序优化
  • 应遵循索引键的最佳左前缀法则
  • 当无法使用索引列,增大max_length_for_sort_data参数的设置 和增大sort_buffer_ size参数的设置
  • where 高于having ,能写在where限定的条件就不要去having中限定了



相关实践学习
如何快速连接云数据库RDS MySQL
本场景介绍如何通过阿里云数据管理服务DMS快速连接云数据库RDS MySQL,然后进行数据表的CRUD操作。
MySQL数据库入门学习
本课程通过最流行的开源数据库MySQL带你了解数据库的世界。 &nbsp; 相关的阿里云产品:云数据库RDS MySQL 版 阿里云关系型数据库RDS(Relational Database Service)是一种稳定可靠、可弹性伸缩的在线数据库服务,提供容灾、备份、恢复、迁移等方面的全套解决方案,彻底解决数据库运维的烦恼。 了解产品详情:&nbsp;https://www.aliyun.com/product/rds/mysql&nbsp;
目录
相关文章
|
7月前
|
存储 SQL 关系型数据库
mysql底层原理:索引、慢查询、 sql优化、事务、隔离级别、MVCC、redolog、undolog(图解+秒懂+史上最全)
mysql底层原理:索引、慢查询、 sql优化、事务、隔离级别、MVCC、redolog、undolog(图解+秒懂+史上最全)
mysql底层原理:索引、慢查询、 sql优化、事务、隔离级别、MVCC、redolog、undolog(图解+秒懂+史上最全)
|
7月前
|
存储 关系型数据库 MySQL
MySQL数据库索引的数据结构?
MySQL中默认使用B+tree索引,它是一种多路平衡搜索树,具有树高较低、检索速度快的特点。所有数据存储在叶子节点,非叶子节点仅作索引,且叶子节点形成双向链表,便于区间查询。
224 4
|
9月前
|
存储 关系型数据库 MySQL
阿里面试:MySQL 一个表最多 加几个索引? 6个?64个?还是多少?
阿里面试:MySQL 一个表最多 加几个索引? 6个?64个?还是多少?
阿里面试:MySQL 一个表最多 加几个索引? 6个?64个?还是多少?
|
8月前
|
SQL 缓存 关系型数据库
MySQL 慢查询是怎样优化的
本文深入解析了MySQL查询速度变慢的原因及优化策略,涵盖查询缓存、执行流程、SQL优化、执行计划分析(如EXPLAIN)、查询状态查看等内容,帮助开发者快速定位并解决慢查询问题。
352 0
|
11月前
|
关系型数据库 MySQL 数据库
Mysql的索引
MYSQL索引主要有 : 单列索引 , 组合索引和空间索引 , 用的比较多的就是单列索引和组合索引 , 空间索引我这边没有用到过 单列索引 : 在MYSQL数据库表的某一列上面创建的索引叫单列索引 , 单列索引又分为 ● 普通索引:MySQL中基本索引类型,没有什么限制,允许在定义索引的列中插入重复值和空值,纯粹为了查询数据更快一点。 ● 唯一索引:索引列中的值必须是唯一的,但是允许为空值 ● 主键索引:是一种特殊的唯一索引,不允许有空值 ● 全文索引: 只有在MyISAM引擎、InnoDB(5.6以后)上才能使⽤用,而且只能在CHAR,VARCHAR,TEXT类型字段上使⽤用全⽂文索引。
|
SQL 关系型数据库 MySQL
MySQL进阶突击系列(07) 她气鼓鼓递来一条SQL | 怎么看执行计划、SQL怎么优化?
在日常研发工作当中,系统性能优化,从大的方面来看主要涉及基础平台优化、业务系统性能优化、数据库优化。面对数据库优化,除了DBA在集群性能、服务器调优需要投入精力,我们研发需要负责业务SQL执行优化。当业务数据量达到一定规模后,SQL执行效率可能就会出现瓶颈,影响系统业务响应。掌握如何判断SQL执行慢、以及如何分析SQL执行计划、优化SQL的技能,在工作中解决SQL性能问题显得非常关键。
|
6月前
|
缓存 关系型数据库 MySQL
降低MySQL高CPU使用率的优化策略。
通过上述方法不断地迭代改进,在实际操作中需要根据具体场景做出相对合理判断。每一步改进都需谨慎评估其变动可能导致其他方面问题,在做任何变动前建议先在测试环境验证其效果后再部署到生产环境中去。
280 6
|
7月前
|
存储 SQL 关系型数据库
MySQL 核心知识与索引优化全解析
本文系统梳理了 MySQL 的核心知识与索引优化策略。在基础概念部分,阐述了 char 与 varchar 在存储方式和性能上的差异,以及事务的 ACID 特性、并发事务问题及对应的隔离级别(MySQL 默认 REPEATABLE READ)。 索引基础部分,详解了 InnoDB 默认的 B+tree 索引结构(多路平衡树、叶子节点存数据、双向链表支持区间查询),区分了聚簇索引(数据与索引共存,唯一)和二级索引(数据与索引分离,多个),解释了回表查询的概念及优化方法,并分析了 B+tree 作为索引结构的优势(树高低、效率稳、支持区间查询)。 索引优化部分,列出了索引创建的六大原则
186 2
|
8月前
|
存储 关系型数据库 MySQL
MySQL覆盖索引解释
总之,覆盖索引就像是图书馆中那些使得搜索变得极为迅速和简单的工具,一旦正确使用,就会让你的数据库查询飞快而轻便。让数据检索就像是读者在图书目录中以最快速度找到所需信息一样简便。这样的效率和速度,让覆盖索引成为数据库优化师傅们手中的尚方宝剑,既能够提升性能,又能够保持系统的整洁高效。
259 9
|
9月前
|
存储 SQL 关系型数据库
京东面试:mysql深度分页 严重影响性能?根本原因是什么?如何优化?
京东面试:mysql深度分页 严重影响性能?根本原因是什么?如何优化?
京东面试:mysql深度分页 严重影响性能?根本原因是什么?如何优化?

推荐镜像

更多