侧边栏壁纸
博主头像
Terry

『LESSON 5』

  • 累计撰写 90 篇文章
  • 累计创建 21 个标签
  • 累计收到 1 条评论

目 录CONTENT

文章目录

MySQL explain详解

Terry
2020-08-22 / 0 评论 / 0 点赞 / 605 阅读 / 4,424 字 / 正在检测是否收录...

MySQL8.0 explain详解

详情看了官网 https://dev.mysql.com/doc/refman/8.0/en/explain-output.html
EXPLAIN返回 SELECT 语句中使用的每个表的一行信息。它按 MySQL 在处理语句时读取它们的顺序列出输出中的表。这意味着 MySQL 从第一个表中读取一行,然后在第二个表中查找匹配的行,然后在第三个表中查找匹配的行,等等。处理所有表时,MySQL 将输出所选列,并通过表列表回溯,直到找到具有更多匹配行的表。下一行从此表中读取,该过程将继续使用下一个表。

输出列信息

id 标识符SELECT

SELECT标识符,查询中SELECT的序列号

select_type 类型SELECT

SELECT的类型,可以是下面显示的任何类型.

  • SIMPLE 简单选择.没有使用UNION或者子查询操作
  • PRIMARY 查询中最外层的SELECT(包括UNION和子查询)
  • UNION UNION操作中,查询的第二个或后一个SELECT语句
  • DEPENDENT UNION操作中,查询中处于内层的SELECT(内层的SELECT语句与外层的SELECT语句有依赖关系)
  • UNION RESULT UNION操作的结果,id值通常为NULL
  • SUBQUERY 子查询中首个SELECT(如果有多个子查询存在)
  • DEPENDENT SUBQUERY 子查询中的首个SELECT,取决于外部查询
  • DERIVED 派生表(子查询位于FROM子句)
  • DEPENDENT DERIVED 依赖于另一个表的派生表
  • MATERIALIZED 被物化的子查询
  • UNCACHEABLE SUBQUERY 无法缓存结果的子查询,必须对外部查询的每一行重新评估
  • UNCACHEABLE UNION 属于不可缓存子查询的UNION中的第二个或更晚选择(参见UNCACHEABLE SUBQUERY)

table 输出行的表

表名

partitions 匹配的分区

记录将由查询匹配的记录的分区。该值用于非分区表。

type 联接类型

以下列表描述了联接类型,从最佳类型到最差类型排序

  • system 该表只有一行(= 系统表)
  • const 该表最多有一个匹配的行,在查询开始时读取该行。由于只有一行,因此优化器的其余部分可以将该行中列中的值视为常量。 const表非常快,因为它们只读一次。
  • eq_ref 取本表中和关联表表中的每行组合成的一行。除 了 system 和 const 类型之外, 这是最好的联接类型。当连接使用索引的所有部分时, 索引是主键或唯一非 NULL 索引时, 将使用该值。eq_ref 可用于使用 = 运算符比较的索引列。比较值可以是常量或使用此表之前读取的表中的列的表达式。(类似ref,区别在于使用的是唯一索引,使用主键的关联查询)
  • ref 对于每个来自于前面的表的行组合,所有有匹配索引值的行将从这张表中读取。如果不能满足只去一行的情况,会使用索引,则使用ref。如果使用的键仅仅匹配少量行,该联接类型是不错的。(使用非唯一索引扫描或唯一索引前缀扫描,返回单条记录,常出现在关联查询中)
  • fulltext 使用索引执行联接。
  • ref_or_null 此联接类型与ref一样,但添加的是 MySQL 对包含值的行执行额外的搜索。此联接类型优化在解析子查询时最常用。这是对isNull的优化
  • index_merge 此联接类型指示使用索引合并优化。在这种情况下,输出行中的列包含使用的索引列表,并包含使用索引的最长键部分的列表。
  • unique_subquery 该类型替换了下面形式的IN子查询的ref:value IN (SELECT primary_key FROMsingle_table WHERE some_expr);unique_subquery是一个索引查找函数,可以完全替换子查询,效率更高。
  • index_subquery 该联接类型类似于unique_subquery。可以替换IN子查询,但只适合下列形式的子查询中的非唯一索引:value IN SELECT key_column FROM single_table WHERE some_expr)
  • range 仅检索给定范围内的行,使用索引选择行。输出行中的列指示使用哪个索引。包含使用时间最长的关键部分。在该类型中ref列为NULL。当使用=, <>, >, >=, <, <=, IS NULL, <=>, BETWEEN, LIKE, 或者 IN()操作符,用常量比较关键字列时,可以使用range。
  • index 联接类型与ALL相同,只是扫描索引树。当查询仅使用作为单个索引一部分的列时,MySQL 可以使用此联接类型。发生两种方式:
    • 如果索引是查询的覆盖索引,并且可用于满足表中所需的所有数据,则仅扫描索引树。在这种情况下,列中显示 。仅索引扫描通常比ALL 快,因为索引的大小通常小于表数据。Extra: Using index
    • 使用从索引的读取按索引顺序查找数据行,执行完整的表扫描。不显示在列中。Uses indexExtra
  • ALL
    对于每个来自于先前的表的行组合,进行完整的表扫描。如果表是第一个没标记const的表,这通常不好,并且通常在它情况下很差。通常可以增加更多的索引而不要使用ALL,使得行能基于前面的表中的常数值或列值被检索出。

possible_keys 可选择的索引

指出MySQL能使用哪个索引在该表中找到行。注意,该列完全独立于EXPLAIN输出所示的表的次序。这意味着在possible_keys中的某些键实际上不能按生成的表次序使用。

key 实际上选择使用的索引

key列显示MySQL实际决定使用的键(索引)。如果没有选择索引,键是NULL。要想强制MySQL使用或忽视possible_keys列中的索引,在查询中使用FORCE INDEX、USE INDEX或者IGNORE INDEX。

key_len 所选的键的长度

ey_len列显示MySQL决定使用的键长度。如果键是NULL,则长度为NULL。注意通过key_len值我们可以确定MySQL将实际使用一个多部关键字的几个部分。

ref 与索引比较的列

该列显示与列中命名的索引比较的列或常量,以从表中选择行。

rows 需要搜索出的行的估计值

该列指示 MySQL 认为必须检查才能执行查询的行数。

filtered 按表条件筛选的行的百分比

该列指示由表条件筛选的表行的估计百分比。最大值为 100,这意味着未对行进行筛选。从 100 减值表示筛选量增加。 显示检查的行的估计×显示与下表连接的行数。例如,如果 为 1000 且为 50.00 (50%),则要与下表连接的行数为 1000 × 50% = 500。

Extra 其他信息,可以显示出使用索引

此列包含有关 MySQL 如何解决查询的其他信息。

  • const row not found 查询为空,表为空
  • Deleting all rows 对于DELETE,某些存储引擎(如MyISAM)支持一种处理程序方法,该方法以简单而快速的方式删除所有表行。如果引擎使用此优化,将显示此值。
  • Distinct MySQL 正在寻找不同的值,因此在找到第一个匹配行后,它将停止为当前行组合搜索更多行。
  • Full scan on NULL key 当优化器无法使用索引查找访问方法时,子查询优化作为回退策略出现此情况。
  • Not exists MySQL能够对查询进行LEFT JOIN优化,发现1个匹配LEFT JOIN标准的行后,不再为前面的的行组合在该表内检查更多的行。
  • range checked for each record (index map: #) MySQL没有发现好的可以使用的索引,但发现如果来自前面的表的列值已知,可能部分索引可以使用。对前面的表的每个行组合,MySQL检查是否可以使用range或index_merge访问方法来索取行。
  • Using filesort MySQL需要额外的一次传递,以找出如何按排序顺序检索行。通过根据联接类型浏览所有行并为所有匹配WHERE子句的行保存排序关键字和行的指针来完成排序。然后关键字被排序,并按排序顺序检索行。
  • Using index 仅使用索引树中的信息从表中检索列信息,而无需执行其他查找即可读取实际行。当查询仅使用作为单个索引一部分的列时,可以使用此策略。
  • Using index condition 通过访问索引元组并首先测试它们来确定是否读取完整表行来读取表。这样,索引信息用于延迟([向下])读取完整表行,除非有必要。(减少回表)
  • Using index for group-by 与表访问方法类似,指示 MySQL 找到了一个索引,可用于检索 或 查询的所有列,而无需对实际表进行任何额外的磁盘访问。此外,索引以最有效的方式使用,以便对于每个组,只读取几个索引条目。
  • Using index for skip scan 指示使用跳过扫描访问方法。
  • Using sort_union(...), Using union(...), Using intersect(...) 这些函数说明如何为index_merge联接类型合并索引扫描。
  • Using temporary 若要解决查询,MySQL 需要创建一个临时表来保存结果。如果查询包含和子句以不同的方式列出列,通常会发生这种情况。
  • Using where 代表需要回表,如果Extra值不为Using where并且表联接类型为ALL或index,查询可能会有一些错误。
  • Using where && Using index 查询的列被索引覆盖,并且where筛选条件是索引列之一但是不是索引的不是前导列,Extra中为Using where; Using index, 意味着无法直接通过索引查找来查询到符合条件的数据
0

评论区