摘要: SQL语句执行顺序及实际案例
关键词: 数据库、MySQL、SQL
整体说明
本文主要是以MySQL数据库为例,介绍SQL语句执行顺序及其实际案例,为平时编写SQL时,会遇到的比较迷惑的问题,寻找底层思路。
一、SQL顺序概况
平时我们写sql的时候有没有注意sql语句是按照什么顺序执行的呢?
本篇文章就来介绍下这个顺序,参考了《MySQL技术内幕 SQL编程》,有兴趣可以去学习一下。
如上图所示,SQL 的执行顺序是按照这个顺序执行的 总共11个步骤,
第一步是 FROM ,最后一步是 LIMIT ,每个操作都会产生一张虚拟表,这些虚拟表对用户不是透明的,只有最后一步生成的虚拟表才会返回给用户。
具体每一步的内容如下:
- FROM: 对FROM子句中的左表和右表执行笛卡尔积,产生虚拟表VT1
- ON: 对虚拟表VT1应用ON筛选,只有那些符合的行才被插入虚拟表VT2中
- JOIN: 如果指定了OUTER JOIN(如LEFT OUTER JOIN ,RIGTH OUTER JOIN),那么保留表中未匹配的行作为外部行添加到虚拟表VT2中,产生虚拟表VT3。如果FROM子句含两个以上表,则对上一个连接生成的结果表VT3和下一个表重复执行步骤1~步骤3,直到处理完所有的表为止
- WHERE: 对虚拟表VT3应用VT3应用WEHRE过滤条件,只有符合的记录才被插入虚拟表VT4中
- GROUP BY: 根据GROUP BY 子句中的列,对VT4中的记录进行分组操作,产生VT5
- CUBE|ROLLUP: 对表VT5进行CUBE或ROLLUP操作,产生表VT6
- HAVING: 对虚拟表VT6应用HAVING过滤器,只有符合的记录才被插入虚拟表VT7中
- SELECT: 选定指定的列,插入到虚拟表VT8中
- DISTINCT: 去除重复数据,产生虚拟表VT9
- ORDER BY: 将虚拟表VT9中的记录按照进行排序操作,产生虚拟表VT10
- LIMIT: 取出指定行的数据,产生虚拟表VT11,并返回给查询用户
二、数据准备
2.1、数据表结构
CREATE TABLE `student` (
`student_id` int(11) COMMENT "学生id",
`student_name` varchar(255) COMMENT "学生姓名",
`subject` varchar(255) COMMENT "学科名称"
) comment = "学生表";
CREATE TABLE