【MySQL】从执行计划了解MySQL优化策略

这篇具有很好参考价值的文章主要介绍了【MySQL】从执行计划了解MySQL优化策略。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

前言

在MySQL中,执行计划是优化器根据查询语句生成的一种重要的数据结构,它描述了如何通过组合底层操作实现查询的逻辑。当我们编写一条SQL语句时,MySQL会自动对其进行优化,并生成最优的执行计划以实现更快的查询速度。

各位精通MySQL的大佬们,像往常一样,我们经常会遇见一堆SQL查询要处理。作为一个优秀的MySQL的操盘手,不能让这些SQL语句任性地在数据库中胡乱扔,必须要好好管管它们!

但是,面对复杂的SQL语句和复杂的数据库架构,我们如何才能快速和准确地分析查询性能?难道要求神通广大的数据库教父出山帮忙?

不要担心!在MySQL世界中,EXPLAIN命令就像是一个小巧而灵活的工具,能够帮助你轻松解决这些问题。使用它,并结合我们自己的经验和智慧,我们就可以像成功解锁小学奥数一样地优化SQL查询,成为MySQL中的一名优秀演员。

废话不多说,现在就让我们开始吧,让我们去通过熟悉每个查询的执行过程,并用一颗豁达的心态理解每个SQL查询的优化分析!

本文将介绍MySQL执行计划的相关知识。首先我们将介绍执行计划的概念以及MySQL优化器是如何生成执行计划的,然后我们将深入探讨执行计划中各种类型的操作符,最后我们将讨论如何通过执行计划来诊断性能问题。

一、什么是执行计划

执行计划是MySQL优化器为了优化查询而生成的一种数据结构,它记录了数据库系统执行查询时所采取的操作流程,即对查询语句的各部分如何进行处理以最终得到查询结果的过程。执行计划通常被表示为一棵树状结构,节点代表不同的操作符(operator),叶子节点代表访问底层数据的方式,例如表扫描或索引查找等。
【MySQL】从执行计划了解MySQL优化策略,# MySql,mysql,数据库

获取MySQL查询执行计划的方法有多种,下面介绍两种常用的方法:

1.1. 使用EXPLAIN命令

EXPLAIN命令可以帮助我们分析查询的执行计划,帮助我们发现潜在的性能问题。我们可以通过以下命令来使用:

EXPLAIN SELECT *
FROM employees
WHERE salary > 50000;

执行以上命令后,MySQL将返回一张表格,其中包含了查询语句所使用的索引、扫描的行数以及各个步骤的 cost 等信息。

1.2. 使用PROFILING

MySQL提供了一个 PROFILING 工具,能够记录 MySQL 服务器上连接和查询的操作时间,包括每个 SQL 语句执行的时间以及资源的消耗。我们可以通过以下命令来启用 PROFILING:

SET profiling = 1;

然后运行我们要分析的查询语句。
最后,我们可以查看查询的 profile 信息,例如:

SHOW PROFILE ALL FOR QUERY n;

其中 n 表示查询语句的 ID,它可以通过如下命令获取:

SHOW PROFILES;

以上就是获取MySQL执行计划的两种常用方法,你需要根据具体情况选择不同的方法来获取和分析执行计划。

二、执行计划生成过程

在查询过程中,MySQL优化器必须决定查询的最佳执行计划。这个过程通常称为查询优化。查询优化的目标是选择最小代价的执行计划,也就是要在所有可能的执行计划中选择一个最快的执行计划。查询优化可以看作是一个搜索空间的问题,其中搜索空间包括所有可能的执行计划。
以下是MySQL优化器确定执行计划的一般流程:

  • 解析SQL语句并构造语法树。MySQL首先解析SQL语句,并使用语法树表示查询。语法树由各种操作符和表达式组成。

    例如,下面是一个查询语句的语法树:

     SELECT *
        FROM employees
        WHERE salary > 50000;
    
    • 生成所有可能的执行计划。接下来,MySQL优化器将生成所有可能的执行计划。它会尝试所有可能的操作顺序和访问方法,以找到最优的执行计划。
    • 估算每个执行计划的代价。对于每个执行计划,MySQL会估算其代价并选择代价最小的执行计划。代价通常由磁盘I/O,内存使用等因素组成。
    • 执行查询。最后,MySQL执行计划并返回结果。

三、执行计划的操作符

MySQL执行计划中的操作符分为三大类:查询计划操作符、连接操作符和辅助操作符。下面我们将分别介绍这三种操作符。

3.1. 查询计划操作符

查询计划操作符包括以下类型:

  • 表扫描(Table scan):这是一种简单的操作,它通过遍历整个表来检索记录。当表没有索引或索引不能用于查询时,MySQL就会采用这种方式。

查询示例:

SELECT *
    FROM employees;
  • 索引查找(Index lookup):当查询条件中包含索引列或者覆盖索引时,MySQL会使用索引查找操作。这个操作通常比表扫描快很多。

查询示例:

SELECT *
FROM employees
WHERE emp_id = 1001;
  • 范围查找(Range lookup):当查询条件中包含范围操作符(如>、<、BETWEEN、IN等)时,MySQL会采用范围查找操作。

查询示例:

SELECT *
FROM employees
WHERE salary BETWEEN 40000 AND 60000;
  • 全文搜索(Fulltext search):当需要在全文中搜索某个关键字时,MySQL会采用全文搜索操作。但是它要求表必须有全文索引。

查询示例:

SELECT *
FROM articles
WHERE MATCH(title, body) AGAINST ('MySQL');
  • 排序(Sort):当查询需要按照指定的排序规则显示结果时,MySQL采用排序操作。

查询示例:

SELECT *
FROM employees
ORDER BY salary DESC;
  • 分组(Group):当需要对结果集分组时,MySQL会采用分组操作符。

查询示例:

SELECT department, AVG(salary)
FROM employees
GROUP BY department;
  • 聚合(Aggregation):当需要对整个表或者某一部分进行聚合操作时,MySQL采用聚合操作符。

查询示例:

SELECT COUNT(*)
FROM employees;

3.2. 连接操作符

连接操作符用于将不同数据源的数据进行连接。MySQL支持以下几种连接操作符:

  • 等值连接(Equal join):当两个表中包含相同的关键字(也就是外键)时,MySQL会使用等值连接操作符实现连接操作。

查询示例:

SELECT *
FROM employees JOIN departments
ON employees.department_id = departments.department_id;
  • 非等值连接(Non-equal join):当连接条件使用非等于运算符时(如>、<、BETWEEN等),MySQL会使用非等值连接操作符。

查询示例:

SELECT *
FROM employees JOIN salaries
ON employees.emp_id = salaries.emp_id AND salaries.salary > 50000;
  • 自连接(Self join):也称为自连接操作,它将一个表与其自身进行连接。

查询示例:

SELECT a.emp_name AS name1, b.emp_name AS name2
FROM employees a, employees b
WHERE a.manager_id = b.emp_id;
  • 外连接(Outer join):当我们需要查询两个表的记录时,无论这两个表是否存在相同的关键字,我们都可以使用外连接操作符进行连接。

查询示例:

SELECT *
FROM employees LEFT JOIN salaries
ON employees.emp_id = salaries.emp_id;

3.3. 辅助操作符

辅助操作符是MySQL执行计划中的其他操作。这些操作通常用于优化性能,包括以下几种类型:

  • 索引合并(Index merge):当查询涉及多个索引时,MySQL会将这些索引进行合并来提高性能。

查询示例:

SELECT *
FROM employees
WHERE emp_id = 1001 AND salary > 50000;
  • 子查询(Subquery):当一个查询需要嵌套在另一个查询之内时,MySQL会使用子查询操作符。

查询示例:

SELECT *
FROM employees
WHERE salary > (SELECT AVG(salary) FROM employees);
  • 临时表(Temporary table):当查询涉及到大量数据或者存在复杂的连接关系时,MySQL会在磁盘上创建一个临时表来处理查询。

查询示例:

SELECT *
FROM employees JOIN salaries JOIN departments
ON employees.emp_id = salaries.emp_id AND employees.department_id = departments.department_id;

以上就是MySQL执行计划中各种操作符的介绍。这些操作符在执行计划生成和性能优化中都会扮演重要的角色。

四、执行计划的诊断分析

当我们发现MySQL的性能有问题时,我们可以通过执行计划来诊断性能问题。下面是一些常用的技巧:

4.1. 使用EXPLAIN命令

EXPLAIN命令可以帮助我们分析查询的执行计划,帮助我们发现潜在的性能问题。我们可以通过以下命令来使用:

EXPLAIN SELECT *
FROM employees
WHERE salary > 50000;

输出结果将告诉我们MySQL所采取的操作顺序和访问方式以及每个操作的代价。

4.2. 检查索引

在许多情况下,我们可以通过添加适当的索引来提高查询性能。我们可以使用以下命令检查表上的索引:

SHOW INDEXES FROM employees;

输出结果将告诉我们索引的名称,类型,所包含的列等信息。

4.3. 分析查询日志

我们可以通过查看MySQL的查询日志来分析查询的执行情况。我们可以使用以下命令启用查询日志:
ini复制代码SET GLOBAL general_log = ‘ON’;

然后,我们可以查看查询日志文件,例如:

ail -f /var/log/mysql/general.log

以上就是使用执行计划诊断MySQL性能问题的基本技巧。在实际工作中,我们可以根据具体情况采用不同的方法来分析执行计划并优化查询性能。

五、如何分析 EXPLAIN 结果?

在使用EXPLAIN命令获取MySQL查询执行计划后,我们需要对结果进行分析,以便识别潜在的性能问题。以下是一些常用的分析方法:

5.1. 扫描类型

扫描类型(Scan Type)是显示在查询计划耗时列中的一项指标。通过这个指标,我们可以了解MySQL是否使用了索引或者全表扫描来访问数据。通常情况下,如果出现 ALL、index 和 range 等扫描类型,就意味着性能可能受到影响。其中:

  • ALL 表示全表扫描,即扫描了整个表的数据。
  • index 表示使用了索引扫描,但需要在索引中查找需要的记录。
  • range 表示使用了索引范围查找,即使用了部分索引进行查找。

5.2. 关联类型

关联类型是指在连接操作中使用的算法。如果查询计划中出现了 Equa Join、Ref、Index Merge 等关联类型,说明MySQL在执行查询时能够充分利用索引,这通常能提高查询性能。其中:

  • Equa Join表示MySQL使用等值连接(内连接),处理两张表中相同键值的行。
  • Ref表示MySQL使用非等值连接,处理两张表中不同键值的行。
  • Index Merge表示MySQL使用了索引合并算法,将多个索引合并来加速查询。

5.3. 访问类型

访问类型(Access Type) 是指 MySQL 在执行查询时,如何获取数据的方式。常见的访问类型包括:

  • Index: 表示使用了覆盖索引来访问表中的数据,即只需要使用索引就可以获取所需的数据。
  • Index-full scan: 表示使用了全表扫描索引的方式来获取数据,但只访问了索引部分的数据。
  • Full-text: 表示使用了全文搜索来获取数据。

5.4. 行数估算

查询计划中的 rows 列表示执行某个步骤时,MySQL 估算的行数。如果进行查询的表很大或者存在大量的数据,则行数估算可能会存在偏差。这种情况下,我们需要特别关注具体的查询步骤和访问类型,以确定是否存在性能问题。

5.5. 性能优化

根据查询执行计划,我们可以判断是否有性能瓶颈,需要对 SQL 查询语句进行优化。优化建议取决于具体的查询计划,例如:

  • 在查询计划中使用了索引,请确保使用正确的索引并创建合适的索引来支持查询。
  • 如果查询计划使用了全表扫描,请尝试减少查询的数据量以避免全表扫描。
  • 如果查询计划中出现了文件排序或临时表操作,请考虑通过更改查询语句或优化表结构来避免这些操作。

5.6. 场景分析

给大家举一个具体的示例来详细说明如何分析 EXPLAIN 结果。
假设我们有以下查询语句:

EXPLAIN SELECT *
FROM orders o JOIN customers c ON o.customer_id = c.customer_id
WHERE o.order_date >= '2022-01-01' AND c.address LIKE '%Beijing%';

得到的查询计划结果如下:

+----+-------------+-------+------------+------+---------------+------+---------+-----------------------------+------+----------+----------------+
| id | select_type | table | partitions | type | possible_keys | key  | key_len | ref                         | rows | filtered | Extra          |
+----+-------------+-------+------------+------+---------------+------+---------+-----------------------------+------+----------+----------------+
|  1 | SIMPLE      | c     | NULL       | ALL  | PRIMARY       | NULL | NULL    | NULL                        | 1000 |   100.00 | Using where    |
|  1 | SIMPLE      | o     | NULL       | ref  | customer_id   | customer_id | 4       | worldsql.c.customer_id |    2 |    11.11 | Using index    |
+----+-------------+-------+------------+------+---------------+------+---------+-----------------------------+------+----------+----------------+

我们将根据这个查询计划结果可以进行如下分析:
(1)扫描类型
在这个查询计划中,第一行表示 customers 表的扫描类型是 ALL,即执行了全表扫描。这通常会降低MySQL查询性能,因此我们应该检查是否在表上创建了适当的索引来优化查询。
(2)关联类型
关联类型是 SIMPLE,表示这是一个简单的非子查询。同时,我们还可以看到这里使用了 Equa Join 算法,即使用内连接处理两张表中相同键值的行。这通常是MySQL执行联接操作时的最佳算法之一。
(3)访问类型
在这个查询计划中,我们还可以看到,orders 表使用了 ref 访问类型,即使用了索引扫描来获取所需数据。这通常比全表扫描更加高效,因此这是一个好的访问类型。
(4) 行数估算
在这个查询计划中,rows 行数估算列显示为 1000,而实际上 customers 表中只有 1000 行。这意味着MySQL执行了全表扫描并扫描了整个表的所有行。这通常会影响查询性能,因此我们应该检查表上是否存在适当的索引。
(5)性能优化
针对以上分析结果,我们可以考虑以下优化策略:

  • 创建索引:为 customers 表上的 address 列创建索引,以避免全表扫描。
  • 设计合适的索引:为 orders 表上的 order_date 和 customer_id 列创建复合索引来支持查询,可以进一步提高查询性能。

实际sql查询执行,借助通过分析 EXPLAIN 的结果,我们可以确定如何针对性地优化查询语句以提高性能。

六、总结

EXPLAIN 命令就像是一个卧虎藏龙的武林秘籍,使用它能够让MySQL查询变得轻松愉快。在这里,我们可以看到每个查询都是一场表演,有着自己的角色和特点。

扫描类型就像是一个吃货,它会吃遍整个表才能满足胃口;而关联类型就像是一个心机婊,它总是喜欢暗示你要去找另外的表玩耍。而访问类型则是一个聪明的程序员,它总是想方设法通过索引快速获取所需数据。

然而,行数估算却像是一个嘴巴不太靠谱的推销员,它总是高估自己的能力,并且喜欢随意地浪费时间和精力。

幸运的是,在这个MySQL世界中,你永远不会孤单。通过使用 EXPLAIN 命令并对查询计划结果进行分析,我们可以更好地理解MySQL执行查询的过程,找到性能瓶颈,并采取相应的优化措施。

最后,要记住:优化MySQL查询不仅需要技能,还需要耐心和毅力。但是,当你看到查询计划明显优化后,你会感觉整个人都充满了力量和信心!

言归正传,MySQL是一个功能强大的数据库系统,它可以应用于许多不同的场景。为了发挥其最大的性能潜力,我们需要深入了解MySQL的执行计划和查询优化技术,并使用这些知识来诊断和优化查询性能。文章来源地址https://www.toymoban.com/news/detail-576219.html

到了这里,关于【MySQL】从执行计划了解MySQL优化策略的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • MySQL 执行计划详解

    本文基于MySQL 8.0编写,理论支持MySQL 5.0及更高版本。 id :该语句的唯一标识。如果explain的结果包括多个id值,则数字越大越先执行;而对于相同id的行,则表示从上往下依次执行。 select_type :查询类型,有如下几种取值: table :表示当前这一行正在访问哪张表,如果SQL定义

    2024年02月13日
    浏览(43)
  • MYSQL EXPLAIN 执行计划

    有了慢查询语句后,就要对语句进行分析。一条查询语句在经过 MySQL 查询优化器的各种基于成本和规则的优化会后生成一个所谓的执行计划,这个执行计划展示了接下来具体执行查询的方式,比如多表连接的顺序是什么,对于每个表采用什么访问方法来具体执行查询等等。

    2024年02月05日
    浏览(46)
  • MySQL的执行计划详解(Explain)

    在 MySQL 中可以通过 explain 模拟优化器执行 SQL语句,从而知道 MySQL 是如何处理 SQL 语句的。 • 客户端向 MySQL 服务器发送一条查询请求 • 服务器首先检查查询缓存,如果命中缓存,则立刻返回存储在缓存中的结果。否则进入下一阶段 • 服务器进行 SQL 解析、预处理、

    2023年04月26日
    浏览(54)
  • 超级详解MySQL执行计划explain

            要对执行计划有个比较好的理解,需要先对MySQL的基础结构及查询基本原理有简单的了解。          MySQL本身的功能架构分为三个部分,分别是 应用层、逻辑层、物理层,不只是MySQL ,其他大多数数据库产品都是按这种架构来进行划分的。 应用层,主要负责与客

    2023年04月15日
    浏览(41)
  • MySQL视图、索引、导入导出、执行计划

    目录 一、前言 1.导读 2.学习的好处 二、视图 1.什么是视图 2.视图与数据表的区别 3.使用视图的优点 4.视图的语法 1.创建视图(CREATE VIEW) 2.查询视图数据 3.更新视图数据 4.修改视图定义(ALTER VIEW) 5.删除视图(DROP VIEW) 三、索引 1.什么是索引 2.为什么要使用索引 3.索引的优缺

    2024年02月13日
    浏览(47)
  • Mysql中explain执行计划信息中字段详解

    2.1 id 每个select子句的执行顺序,相同从上到下,不同由大到小执行 2.2 select_type select语句类型 SIMPLE 简单的select查询,查询中不包含子查询或者UNION PRIMARY 查询中若包含任何复杂的子部分,最外层查询则被标记为PRIMARY SUBQUERY 在SELECT或WHERE列表中包含了子查询 DERIVED 在FROM列表中包

    2024年02月10日
    浏览(42)
  • MySql中执行计划如何来的——Optimizer Trace

    作者:京东物流 籍磊 当谈到MySQL的执行计划时,会有很多同学想:“我就觉得使用其他的执行方案比EXPLAIN语句输出的方案强,凭什么优化器做的决定与我得不一样?”。这个问题在MySQL 5.6之前或许自己很难解决,但是现在MySQL5.6及更高的版本中引入了Optimizer Trace。 当下面这

    2023年04月26日
    浏览(33)
  • mysql执行计划之Extra列-Using where

    顾名思义, Extra 列是用来说明一些额外信息的, 我们可以通过这些额外信息来更准确的理解 MySQL 到底将如何执行给定的查询语句。 MySQL 提供的额外信息很多。这里单说 Using where。 Using where 只是表示 MySQL 使用 where 子句中的条件对记录进行了过滤。与是否全表扫描或读取了索

    2024年02月04日
    浏览(42)
  • TiDB与MySQL的SQL差异及执行计划简析

    作者:京东零售 肖勇 TiDB作为NewSQL,其在对MySQL(SQL92协议)的兼容上做了很多,MySQL作为当下使用较广的事务型数据库,在IT界尤其是互联网间使用广泛,那么对于开发人员来说,1)两个数据库产品在SQL开发及调优的过程中,都有哪些差异?在系统迁移前需要提前做哪些准备

    2023年04月17日
    浏览(33)
  • MySql中执行计划如何来的——Optimizer Trace | 京东云技术团队

    作者:京东物流 籍磊 当谈到MySQL的执行计划时,会有很多同学想:“我就觉得使用其他的执行方案比EXPLAIN语句输出的方案强,凭什么优化器做的决定与我得不一样?”。这个问题在MySQL 5.6之前或许自己很难解决,但是现在MySQL5.6及更高的版本中引入了Optimizer Trace。 当下面这

    2024年02月01日
    浏览(40)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包