【MySQL笔记】ORDER BY是如何工作的?

本文涉及的产品
云数据库 RDS MySQL,集群系列 2核4GB
推荐场景:
搭建个人博客
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
RDS MySQL Serverless 高可用系列,价值2615元额度,1个月
简介: 每次业务功能中总有按操作时间排序,或者按其他字段排序的需求,一想到排序我们就会想到MySQL中的ORDER BY,那在使用的过程中,我们是否会存在不合理的使用导致查询的速度下降呢?

前言

大家好,我是小郭,每次业务功能中总有按操作时间排序,或者按其他字段排序的需求,一想到排序我们就会想到MySQL中的ORDER BY,那在使用的过程中,我们是否会存在不合理的使用导致查询的速度下降呢?

从Using filesort文件排序角度来看排序

为什么一个简单的ORDER BY却有这么大的魔力?

explain select t.passenger_uuid ,t.order_no from yy_order t order by t.order_no limit 1000;

explain分析结果

id select_type table partitions type possible_keys key key_len ref rows filtered Extra
1 SIMPLE t NULL ALL NULL NULL NULL NULL 458420 100 Using filesort

filesort文件排序方式,利用trace工具可以分析

1. 全字段排序(单路)

步骤:

  1. 初始化sort_buffer,将t.passenger_uuid和order_no放入
  2. 从索引中找到满足的条件的主键ID,获取整行数据,存入sort_buffer中
  3. 对sort_buffer中的数据按照字段做快熟排序

在什么情况下会使用外部排序呢?

当排序的数量大于sort_buffer_size时候才会使用外部排序,需要临时表的辅助。

2. rowid排序(双路)

新的算法放入 sort_buffer 的字段,只有要排序的列(order_no)和主键 id。

遍历结果取前1000行数据,再按id查询所需要的字段

查询排序长度参数

show variables like  '%max_length_for_sort_data%';
Variable_name Value
max_length_for_sort_data 1024

字段长度之和小于max_length_for_sort_data  单路排序全字段放入内存中排序 否则 双路排序 rowid和排序字段放入sort_buffer

与全字段排序,不同的是因为内存不足,存入sort_buffer的字段可能就是值存入order_no和Id,遍历排序结果,按照id取出其他的字段。

从这里体现MySQL的一个设计思想:如果内存够,就要多利用内存,尽量减少磁盘访问。

实践

通过order by 随机值触发临时表

-- 根据随机值进行排序
mysql> explain select word from words order by rand() limit 3;
+----+-------------+-------+------------+------+---------------+------+---------+------+------+----------+---------------------------------+
| id | select_type | table | partitions | type | possible_keys | key  | key_len | ref  | rows | filtered | Extra                           |
+----+-------------+-------+------------+------+---------------+------+---------+------+------+----------+---------------------------------+
|  1 | SIMPLE      | words | NULL       | ALL  | NULL          | NULL | NULL    | NULL | 9980 |   100.00 | Using temporary; Using filesort |
+----+-------------+-------+------------+------+---------------+------+---------+------+------+----------+---------------------------------+
1 row in set, 1 warning (0.00 sec)

通过Extra可以看出使用了临时表

# Time: 2021-04-28T06:56:04.664998Z
# User@Host: root[root] @  [172.17.0.1]  Id:    10
# Query_time: 0.003869  Lock_time: 0.000053 Rows_sent: 3  Rows_examined: 10003
SET timestamp=1619592964;
/* ApplicationName=DataGrip 2019.2.5 */ select word from words order by rand() limit 3;

一共扫描了10003行

  1. 创建临时表,建立字段word和id
  2. rank()随机数和word字段,存入临时表,扫描10000行
  3. 初始化sort_buffer从临时表中读取数据,在sort_buffer中进行排序
  4. 取出limit 3,依次从临时表读取word,访问了表的三行数据,扫描3行。

order by rand() 使用了内存临时表,内存临时表排序的时候使用了 rowid 排序方法。

优化器优先考虑,排序的行越小越好。

什么时候会转成磁盘临时表?

mysql> show variables like  '%tmp_table_size%';
+----------------+----------+
| Variable_name  | Value    |
+----------------+----------+
| tmp_table_size | 16777216 |
+----------------+----------+
1 row in set (0.01 sec)

参数:tmp_table_size,默认16M,大于16M就会转换成磁盘临时表

总结

我们发现与全字段排序不同之处:因为内存不足,rowid排序中存入sort_buffer的字段可能就是值存入order_no和Id,遍历排序结果,按照id取出其他的字段。

MySQL 的一个设计思想:如果内存够,就要多利用内存,尽量减少磁盘访问


相关实践学习
如何在云端创建MySQL数据库
开始实验后,系统会自动创建一台自建MySQL的 源数据库 ECS 实例和一台 目标数据库 RDS。
全面了解阿里云能为你做什么
阿里云在全球各地部署高效节能的绿色数据中心,利用清洁计算为万物互联的新世界提供源源不断的能源动力,目前开服的区域包括中国(华北、华东、华南、香港)、新加坡、美国(美东、美西)、欧洲、中东、澳大利亚、日本。目前阿里云的产品涵盖弹性计算、数据库、存储与CDN、分析与搜索、云通信、网络、管理与监控、应用服务、互联网中间件、移动服务、视频服务等。通过本课程,来了解阿里云能够为你的业务带来哪些帮助     相关的阿里云产品:云服务器ECS 云服务器 ECS(Elastic Compute Service)是一种弹性可伸缩的计算服务,助您降低 IT 成本,提升运维效率,使您更专注于核心业务创新。产品详情: https://www.aliyun.com/product/ecs
相关文章
|
1月前
|
Java 关系型数据库 MySQL
自动化测试项目实战笔记(一):JDK、Tomcat、MySQL、Jpress环境安装和搭建
这篇文章是关于自动化测试项目实战笔记,涵盖了JDK、Tomcat、MySQL、Jpress环境的安装和搭建过程,以及测试用例和常见问题总结。
49 1
自动化测试项目实战笔记(一):JDK、Tomcat、MySQL、Jpress环境安装和搭建
|
1月前
|
SQL 搜索推荐 关系型数据库
MySQL 如何实现 ORDER BY 排序?
本文详细解析了MySQL中`ORDER BY`的实现原理及优化方法。通过解析与优化、执行及多种优化技术,如索引利用、内存排序、外部排序等,帮助你提升排序性能。了解其背后的机制,可显著优化查询效率。
30 4
|
1月前
|
SQL 搜索推荐 关系型数据库
MySQL 如何实现 ORDER BY 排序?
在实际开发中,我们经常会使用 MySQL 的 `ORDER BY`进行排序,那么,`ORDER BY`是如何实现的排序的?我们该如何优化 `ORDER BY`的排序性能?这篇文章,我们来聊一聊。
26 3
|
6月前
|
SQL 存储 关系型数据库
Mysql优化提高笔记整理,来自于一位鹅厂大佬的笔记,阿里P7亲自教你
Mysql优化提高笔记整理,来自于一位鹅厂大佬的笔记,阿里P7亲自教你
|
3月前
|
关系型数据库 MySQL 数据处理
Mysql关于同时使用Group by和Order by问题
总的来说,`GROUP BY`和 `ORDER BY`的合理使用和优化,可以在满足数据处理需求的同时,保证查询的性能。在实际应用中,应根据数据的特性和查询需求,合理设计索引和查询结构,以实现高效的数据处理。
537 1
|
3月前
|
SQL 存储 关系型数据库
运维笔记.MySQL.基于mysqldump数据备份与恢复
运维笔记.MySQL.基于mysqldump数据备份与恢复
53 0
|
3月前
|
SQL 关系型数据库 MySQL
【go笔记】使用sqlx操作MySQL
【go笔记】使用sqlx操作MySQL
|
5月前
|
存储 关系型数据库 MySQL
Mysql优化之索引相关介绍(笔记)
索引查找从顶层节点开始查找,通过key值,也就是主键的值进行比较,最终定位到存储数据的叶子节点上面,从叶子节点取出响应的数据。
58 0
Mysql优化之索引相关介绍(笔记)
|
6月前
|
存储 SQL 关系型数据库
MySQL万字超详细笔记❗❗❗
MySQL万字超详细笔记❗❗❗
152 1
MySQL万字超详细笔记❗❗❗
|
5月前
|
存储 关系型数据库 MySQL
技术笔记:MySQL数据库优化详解(收藏)
技术笔记:MySQL数据库优化详解(收藏)
58 0