技本功丨请带上纸笔刷着看:解读MySQL执行计划的type列和extra列

本萌最近被一则新闻深受鼓舞,西工大硬核“女学神”白雨桐,获6所世界顶级大学博士录取

货真价值的才貌双全,别人家的孩子

高考失利与心仪的专业失之交臂,选择了软件工程这门自己完全不懂的专业.即便全部归零,也要证明自己,连续3年专业综合排名第一,各种获奖经历写满了5页PPT。成功始于不断的努力和拼搏,在学习和实践中不断提升自己。

#技本功#愿做你成功路上的基石,赶紧来接收今日份的精神投食~

一、解读type

执行计划的type表示访问数据类型,有很多种访问类型。

1、system
表示这一步只返回一行数据,如果这一步的执行对象是一个驱动表或者主表,那么被驱动表或者子查询只是被访问一次。

2、const

表示这个执行步骤最多只返回一行数据。const通常出现在对主键或唯一索引的等值查询中,例如对表t主键id的查询:

3、eq_ref

eq_ref类型一般意味着在表关联时,被关联表上的关联列走的是主键或者唯一索引。例如,表jiang关联lock_test表,关联列分别是两张表的主键列 :

上面SQL执行时,jiang表是驱动表,lock_test是被驱动表,被驱动表的关联列是主键id,type类型为eq_ref。

所以,对于eq_ref类型来说有一个重要的特点就是:这一步涉及到的表是被驱动表;这一步中使用到唯一索引或主键。除了system和const之外,这是效果最好的关联类型。

4、ref

与上面相反,如果执行计划的某一步的type是ref的话,表示这一步的关联列是非唯一索引。例如,用表jiang的主键id列关联表lock_test的num列,num列上建立了普通索引:

上面SQL执行时,表jiang是驱动表,lock_test是被驱动表,被驱动表上走的是非唯一索引,type类型为ref。

所以ref的特点是:表示这一步访问数据使用的索引是非唯一索引。

5、Ref_or_null
例如执行下面语句:

表示走了索引(num列上有索引),但是也访问了空值。

6、index_merge

表示索引合并,一般对多个二级索引列做or操作时就会发生索引合并。
例如执行下列语句:
mysql> explain select * from lock_test where id=3 or num=4;

id为主键,num列上建有普通索引,语句执行时,会通过两个单列索引来处理or操作。

7、unique_subquery
表示唯一子查询。例如有如下语句执行时:
value in(select primary_key from single_table where ...)
对于in子句来说,当in子句里的子查询返回的是某一个表的主键时,type显示为unique subquery。

8、index_subquery
当有如下语句执行时:
value in(select key_column from single_table where ...)
与上面的相似,表示对于in子句来说,当in子句里的子查询返回的是某一个表的二级索引列(非主键列)时,type显示为index_subquery。

9、range:
在有索引的列上取一部分数据。常见于在索引列上执行between and操作。

10、index:
索引全扫描,一般发生在覆盖索引的时候,也就是对有索引列发生一次全扫描。

11、all:
没有索引的全表扫描。
一个特例:

Explain select * from stu limit 1,1;

二、解读extra

1、using where:
一般有两层意思:
表示通过索引访问时,需要再回表访问所需的数据;
过滤条件发生在server层而不是存储引擎层;
如果执行计划中显示走了索引,但是rows值很高,extra显示为using where,那么执行效果就不会很好。因为索引访问的成本主要在回表上,这时可以采用覆盖索引来优化。
通过覆盖索引也能将过滤条件下压,在存储引擎层执行过滤操作,这样效果是最好的。
所以,覆盖索引是解决using where的最有效的手段。

2、using index condition
表示将过滤下压到存储层执行,防止server层过滤过多数据
如果extra中出现了using index condition,说明对访问表数据进行了优化。

3、using temporary
表示语句执行过程中使用到了临时表。以下子句的出现可能会使用到临时表:
order by
group by
distinct
union等
数据不能直接返回给用户,就需要缓存,数据就以临时表缓存在用户工作空间。注意,可能会出现磁盘临时表,需要关注需要缓存的数据的rows。
可以使用索引消除上面的四个操作对应的临时表。

4、using sort_union(indexs)
比如当执行下面语句:

Sname和sphone列上都有索引,这时执行计划的extra项就会显示using sort_union(i_sname,i_spone),表示索引合并。常伴随着index_merge。

5、using MRR:
一般通过二级索引访问表数据的过程是:先访问二级索引列,找到对应的二级索引数据后就得到对应的主键值,然后拿着这个主键值再去访问表,取出行数据。这样取出的数据是按照二级索引排序的。
MRR表示:通过二级索引得到对应的主键值后,不直接访问表而是先存储起来,在得到所有的主键值后,对主键值进行排序,然后再访问表。这样可以大幅减低对表的访问次数,至少实现了顺序访问表。
MRR的一个优点就是提升索引访问表的效率,也就是降低了回表的成本。但是有一个比较大的问题:取出来的数据就不按照二级索引排序了。

6、using join buffer(Block Nested Loop)
BNL主要发生在两个表关联时,被关联的表上没有索引。
BNL表示这样的意思:A关联B,A的关联列上有索引而B的没有。这时就会从A表中取10行数据拿出来放到用户的join buffer空间中,然后再取B上的数据和join buffer中A的关联列进行关联,这时只需要对B表访问一次,也就是B表发生一次全表扫描。
如果join buffer中的10行数据关联完后,就再取10行数据继续和B表关联,一直到A表的所有数据都关联完为止。
从上面可以看出来,这种方式大概效率会提高约90%。

7、using join buffer(Batched Key Access)
一般出现BKA的情况是:表关联时,被驱动表上有索引,但是驱动表返回的行数太多。
当出现上述情况时,就会将驱动表的返回结果集放到用户工作空间的join buffer中,然后取结果集的一条记录去关联被驱动表的索引关联列。得到相应的主键列后并不马上通过这个主键列去被被驱动表中取数据,而是先存放到工作空间中。等到结果集中的所有数据都关联完了,对工作空间中的所有通过关联得到主键列进行排序,然后统一访问被驱动表,从中取数据。这样的好处就是大大降低了访问的次数。
从上面可以看出:BKA用到了MRR技术;BKA适合驱动表返回行数较多、被驱动表访问时走的是索引的情况。
这个功能可以打开或者关闭:
Set optimizer_switch=’mrr=on,batched_key_access=on’;

8、using index for group by
表示通过复合索引完成group by,不用回表。
例如复合索引(a,b),执行语句:select a from tb group by b;时就会出现using index for group by。

9、using index

表示实现了覆盖索引扫描;也就是需要访问的数据都在索引中,不需要回表。在一般情况下,减少不必要的数据访问能够提升效率。

例如对表lock_test取num列上的数据,num列上建立普通索引:

10、using filesort
说明有排序行为,但是不一定是磁盘排序。

11、materialize scan
对物化表的全扫描,因为物化表就是一个临时表,表上没有索引。

原文地址:https://www.cnblogs.com/dtstack/p/10614277.html

时间: 2024-07-30 02:24:43

技本功丨请带上纸笔刷着看:解读MySQL执行计划的type列和extra列的相关文章

技本功丨知否知否,Redux源码竟如此意味深长(下集)

上集回顾 Redux是如何使用的?首先再来回顾一下这个使用demo(谁让这段代码完整地展示了redux的使用) 如果有小伙伴对这段代码不是很理解的话,建议先去学习Redux的使用再来看这篇源码,这样更加事半功倍.通过上段代码,我们拆分几个比较核心的点,我一一列举一下: 1. action的结构是如何的? 2. 如何去定义一个reducer? 3. combineReducers是如何整合多个reducer的? 4. createStore是如何创建一个store? 5.dispatch拿到act

谈一谈SQL Server中的执行计划缓存(上)

原文:谈一谈SQL Server中的执行计划缓存(上) 简介     我们平时所写的SQL语句本质只是获取数据的逻辑,而不是获取数据的物理路径.当我们写的SQL语句传到SQL Server的时候,查询分析器会将语句依次进行解析(Parse).绑定(Bind).查询优化(Optimization,有时候也被称为简化).执行(Execution).除去执行步骤外,前三个步骤之后就生成了执行计划,也就是SQL Server按照该计划获取物理数据方式,最后执行步骤按照执行计划执行查询从而获得结果.但查询

切记ajax中要带上AntiForgeryToken防止CSRF攻击

在程序项目中经常看到ajax post数据到服务器没有加上防伪标记,导致CSRF被攻击,下面小编通过本篇文章给大家介绍ajax中要带上AntiForgeryToken防止CSRF攻击,感兴趣的朋友一起学习吧 经常看到在项目中ajax post数据到服务器不加防伪标记,造成CSRF攻击 在Asp.net Mvc里加入防伪标记很简单在表单中加入Html.AntiForgeryToken()即可. Html.AntiForgeryToken()会生成一对加密的字符串,分别存放在Cookies 和 in

暑假旅行,记得把行李牌带上

发布时间 2014-07-19   暑假到了,家长们是否计划好了带孩子们去哪里玩?两个月长假,肯定要好好放松,特别是快要毕业班的童鞋们和刚毕业的童鞋们,更要好好放松和做好迎战准备了!带着愉悦的心情,咱们旅游去吧,长假旅行,肯定要带上行李了,车站,机场,来来往往人很多,所以为了安全起见,一定要看好自己的行李了! 车站上,机场上,高铁站,人挤人,过安检,行李难免会撞到一起去,拿错了行李的话,估计就可能找不回来了,所以此时,行李牌就显示出了它的作用,标志着喝别人不一样的行李,就是在对别人说,这是我的行

Django 如何让ajax的POST方法带上CSRF令牌

大家知道,在大前端领域,有一种叫做ajax的东东,即"Asynchronous Javascript And XML"(异步 JavaScript 和 XML),它被用来在不刷新页面的情况下,提交和请求数据.如果Django服务器接收的是一个通过ajax发送过来的POST请求的话,那么将很麻烦.何也?因为在ajax中,没有办法像form表单中那样携带{% csrf_token %}令牌.那怎么办呢?好办!在你的前端模版的JavaScript代码处,添加下面的代码: // 使用jQuer

有上下界的网络流3-有源汇带上下界最小流SGU176

题目大意:有一个类似于工业加工生产的机器,起点为1终点为n,中间生产环节有货物加工数量限制,输入u v z c, 当c等于1时表示这个加工的环节必须对纽带上的货物全部加工(即上下界都为z),c等于0表示加工上界限制为z,下界为0,求节点1(起点)最少需要投放多少货物才能传送带正常工作. 解题思路:    1.直接 增设超级源点ss和超级汇点tt并连上附加边,对 当前图 求 无源汇带上下界可行流    2.将图的汇点sd连一条容量无限制的边到图的源点st,再求一遍 无源汇带上下界可行流    3.

有上下界的网络流2-有源汇带上下界网络流ZOJ3229

ZOJ3229题目大意:一个屌丝给m个女神拍照,计划拍照n天,每一天屌丝可以和C个女神拍照,每天拍照数不能超过D张,而且给每个女神i拍照有数量限制[Li,Ri],对于每个女神n天的拍照总和不能少于Gi,如果有解求屌丝最多能拍多少张照,并求每天给对应女神拍多少张照:否则输出-1. 解题思路:        1.增设一源点st,汇点sd,st到第i天连一条上界为Di下界为0的边,每个女神到汇点连一条下界为Gi上界为正无穷的边,对于每一天,当天到第i个女孩连一条[Li,Ri]的边.        2.

【HDU 4940】Destroy Transportation system(数据水/无源无汇带上下界可行流)

Description Tom is a commander, his task is destroying his enemy’s transportation system. Let’s represent his enemy’s transportation system as a simple directed graph G with n nodes and m edges. Each node is a city and each directed edge is a directe

川哥作品,国内唯一开源的智能人机问答系统,同学们请投上您宝贵的一票,多谢支持!

川哥作品,国内唯一开源的智能人机问答系统,同学们请投上您宝贵的一票,多谢支持!投票地址:http://i.100offer.com/projects/74