minjay26
敬畏每一行代码

有时候我们执行MySQL查询的时候,查询语句没有加order by,但是发现结果总是已经按照id排序好了的,难道MySQL就是为了好看给我们排序

 

 

 如上图数据,是我查询了语句

  SELECT * from employees WHERE first_name like "be%";

看结果是按照emp_no排序,其中first_name上是有索引的。

 

 

首先我们需要搞清楚MySQL回表,回表是指在我们利用的索引树(比如上述语句用到的first_name字段索引)的数据不能满足我们select中选中的数据,因为first_name是二级索引(也可以说是非聚簇索引),该索引只能拿到emp_no,first_name字段值,索引select *查询的话就只能到主键索引所在的索引树上获取相应数据。

按照上述查询去first_name索引上匹配的话,我们匹配到的数据肯定是没法保证按照emp_no排序了,但是为啥最终我们看到的数据是按照emp_no排序了呢?其实这是mysql的mrr机制。

 

mrr想要达到的目的就是从磁盘的随机读变成顺序读,因为如果我们直接拿emp_no乱序的数据回表查询,那么就是一个随机读,这个性能是很差的,所以MySQL会在回表之前提前将emp_no数据排序好,这样回表就变成了顺序读,极大提高性能。

 

当我们将mrr关掉 

set optimizer_switch='mrr=off';

再次执行

可以看到emp_no已经是乱序了

 

 

开启mrr后,我们来explain该查询语句,发现extra里显示了Using MRR

 

 

 所以当我们期望查询的结果有序的时候,一定要在查询的语句中加上自己的order by,而不能因为默认排序了,就不加order by,因为MySQL的机制他是不定的。

 

 

posted on 2021-11-26 15:53  minjay26  阅读(1566)  评论(0编辑  收藏  举报