这是子查询还是只是内部联接

时间:2018-07-02 12:37:24

标签: sql oracle subquery inner-join correlated-subquery

我正在研究子查询概念,以下是从维基百科https://en.wikipedia.org/wiki/Correlated_subquery中提取的一个查询

SELECT employees.employee_number, employees.name
   FROM employees INNER JOIN
     (SELECT department, AVG(salary) AS department_average
       FROM employees
       GROUP BY department) AS temp ON employees.department = temp.department
   WHERE employees.salary > temp.department_average;

sql是相关子查询的重写版本,如下所示

 SELECT
   employee_number,
   name,
   (SELECT AVG(salary) 
      FROM employees
      WHERE department = emp.department) AS department_average
   FROM employees AS emp;

现在我的问题是: 重写版本中的sql是子查询吗?我对此很困惑

  INNER JOIN
         (SELECT department, AVG(salary) AS department_average
           FROM employees
           GROUP BY department) AS temp ON employees.department = temp.department
       WHERE employees.salary > temp.department_average;

2 个答案:

答案 0 :(得分:2)

欢迎使用Stackoverflow。当然,这很令人困惑,因此我将通过使用两个不同的表而不使用表别名来简化它。

我想说它是否在FROM子句中,这称为联接:

SELECT employee_id, department_name
  FROM employees JOIN departments USING (department_id);

如果它在WHERE子句中,则称为子查询:

SELECT employee_id
  FROM employees
 WHERE employee_id = (
         SELECT manager_id
           FROM departments
          WHERE employees.employee_id = departments.manager_id);

如果它在SELECT子句中,则称为 scalar 子查询(感谢@Matthew McPeak):

SELECT employee_id,
       (SELECT department_name
          FROM departments
         WHERE departments.department_id = employees.department_id)
  FROM employees;

答案 1 :(得分:1)

不完全是。等效项为left join。即使没有匹配项,相关版本也会将所有行保留在employees表中。 inner join要求匹配。

通常,执行计划不会完全相同,因为SQL引擎事先不知道所有行是否匹配。

在附加过滤条件下,两个版本等效。请注意,由于where子句无法识别列别名,因此相关版本的过滤器需要子查询或CTE。