以查询语句为例,我们看下面的查询语句:
(6)SELECT [DISTINCT | ALL] col1, col2, agg_func(col3) AS alias
(1) FROM t1 JOIN t2
(2) ON (join_conditions)
(3) WHERE where_conditions
(4) GROUP BY col1, col2
(5)HAVING having_condition
(7) UNION [ALL]
...
(8) ORDER BY col1 ASC,col2 DESC
(9)OFFSET m ROWS FETCH NEXT num_rows ROWS ONLY;
以上是 SQL
中各种关键字的编写顺序,前面括号内的数字代表了它们的逻辑执行顺序。也就是说, SQL
并不是按照编写顺序先执行 SELECT
,然后再执行 FROM
子句。从逻辑上讲, SQL
语句的执行顺序如下:
- 首先,
FROM
和JOIN
是SQL
语句执行的第一步。它们的逻辑结果是一个笛卡尔积,决定了接下来要操作的数据集。注意逻辑执行顺序并不代表物理执行顺序,实际上数据库在获取表中的数据之前会使用ON
和WHERE
过滤条件进行优化访问; - 其次,应用
ON
条件对上一步的结果进行过滤并生成新的数据集; - 然后,执行
WHERE
子句对上一步的数据集再次进行过滤。WHERE
和ON
大多数情况下的效果相同,但是外连接查询有所区别,我们将会在下文给出示例; - 接着,基于
GROUP BY
子句指定的表达式进行分组;同时,对于每个分组计算聚合函数 agg_func 的结果。经过GROUP BY
处理之后,数据集的结构就发生了变化,只保留了分组字段和聚合函数的结果; - 如果存在
GROUP BY
子句,可以利用HAVING
针对分组后的结果进一步进行过滤,通常是针对聚合函数的结果进行过滤; - 接下来,
SELECT
可以指定要返回的列;如果指定了DISTINCT
关键字,需要对结果集进行去重操作。另外还会为指定了AS
的字段生成别名; - 如果还有集合操作符(
UNION
、INTERSECT
、EXCEPT
)和其他的SELECT
语句,执行该查询并且合并两个结果集。对于集合操作中的多个SELECT
语句,数据库通常可以支持并发执行; - 然后,应用
ORDER BY
子句对结果进行排序。如果存在GROUP BY
子句或者DISTINCT
关键字,只能使用分组字段和聚合函数进行排序;否则,可以使用FROM
和JOIN
表中的任何字段排序; - 最后,
OFFSET
和FETCH(LIMIT、TOP)
限定了最终返回的行数。