文章目录
filesort
当我们在MySQL执行计划中,遇到了Using filesort,这就证明MySQL在执行这条语句的时候用到了filesort,而没有使用我们的索引进行排序。所以就需要进行优化。
具体filesort的过程如下:
1、根据表的索引或者全表扫描,读取所有满足条件的记录。
2、对与每一行,存储一对值到缓冲区(排序列,行记录指针),一个是排序的索引列的值,即order by用到的列值,和指向该行数据的行指针,缓冲区的大小为sort_buffer_size大小。
3、当缓冲区满后,运行一个快速排序(qsort)来将缓冲区中数据排序,并将排序完的数据存储到一个临时文件,并保存一个存储块的指针,当然如果缓冲区不满,则不会重建临时文件了。
4、重复以上步骤,直到将所有行读完,并建立相应的有序的临时文件。
5、对块级进行排序,这个类似与归并排序算法,只通过两个临时文件的指针来不断交换数据,最终达到两个文件,都是有序的。
6、重复5直到所有的数据都排序完毕。
7、采取顺序读的方式,将每行数据读入内存,并取出数据传到客户端,这里读取数据时并不是一行一行读,读如缓存大小由read_rnd_buffer_size来指定。
优化使用索引排序
我们的目标就是优化为Using index
官网文档里边有很多优化的方法,这里就只列举其中讲到的几点。
1.select字段中只包含索引字段,避免包含无关字段。
SELECT pk, key_part1, key_part2 FROM t1
ORDER BY key_part1, key_part2;
这样避免了filesort,pk是主键,这个也是可以通过索引查询到了。如果使用的话,涉及到了回表,这样操作,还不如直接进行filesort。不管怎样,我们日常开发过程中,都应该避免使用。
2.使用constant查询联合order by
SELECT * FROM t1
WHERE key_part1 = constant
ORDER BY key_part2;
使用了constant查询后,之后对索引进行order by,这样做后大几率会比全表查询效率要好!
3.避免order by条件中一个desc 一个 asc
参考:
https://www.jianshu.com/p/f943991a2e45 (order by优化,避免filesort)