SQL执行顺序

    1. from
    2. join
    3. on (联表时使用)
    4. where
    5. group by(开始使用select中的别名,后面的语句中都可以使用)
    6. avg,sum….
    7. having (使用函数时使用having)
    8. select
    9. distinct
    10. order by
    11. limit

    语法顺序

    1. <SELECT clause> [<FROM clause>] [<WHERE clause>] [<GROUP BY clause>] [<HAVING clause>] [<ORDER BY clause>] [<LIMIT clause>]


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

    除此之外,理解 SQL 的逻辑执行顺序还可以帮助我们避免一些常见的错误,例如以下语句:

    -- 错误示例
    SELECT emp_name AS empname
      FROM employee
     WHERE empname ='张飞';
    

    该语句的错误在于 WHERE 条件中引用了列别名;从上面的逻辑顺序可以看出,执行 WHERE 条件时还没有执行 SELECT 子句,也就没有生成字段的别名。
    另外一个需要注意的操作就是 GROUP BY,例如:

    -- GROUP BY 错误示例
    SELECT dept_id, emp_name, AVG(salary)
      FROM employee
     GROUP BY dept_id;
    

    由于经过 GROUP BY 处理之后结果集只保留了分组字段和聚合函数的结果(group顺序在select前面),示例中的 emp_name 字段已经不存在;从业务逻辑上来说,按照部门分组统计之后再显示某个员工的姓名没有意义。如果需要同时显示员工信息和所在部门的汇总,可以使用窗口函数。扩展:SQL 语法速成手册