SQL子查询执行

时间:2016-03-28 02:09:37

标签: sql

“找到平均工资最高的部门。”

select dept_name
from instructor
group by dept_name
having avg (salary) >= all (select avg (salary)
                            from instructor
                            group by dept_name)

基于上面嵌套的子查询,我对它的执行方式有点困惑。有人可以确认我的解释是否正确吗?

首先,第二行from instructor将运行,并且从该关系开始,元组将按dept_name分组。然后在由dept_name分组的新形成的关系上,您将检查每个组的平均工资,并将值与来自在子查询中形成的新教师关系的所有其他平均工资进行比较。它是否正确?子查询将形成一个新的关系,因此您实际上将有两个独立的关系进行操作?

(select avg (salary)
from instructor
group by dept_name)

在上面的子查询中,我最初认为在group by子句 HAVE 中没有聚合的任何属性都出现在select子句中。但在这种情况下,为什么子查询中的select子句中不存在dept_name

2 个答案:

答案 0 :(得分:0)

group by 中的列必须出现在select中。这种情况是不可能的,因为查询只需要返回一列。

此查询的结果:

select avg(salary)
from instructor
group by dept_name

只是每个部门平均工资的清单。作为查询本身,如果您还有部门名称,这将更有用。但在这种情况下,这是不必要的。

答案 1 :(得分:0)

查询分为两部分。第一个是您的嵌套查询(实际上以Left Anti Semi join执行)。这将返回每个dept_name的平均工资。

--Nested Query Returns all dept_name average salaries
select avg (salary)
from #instructor
group by dept_name

然后将其与使用" All"的主要选择语句中的平均工资进行比较。运营商。这相当于比较所有部门的最高平均工资。把它想象如下:

Main Select       Nested Comparison
Math 200     >=   Max({Math 200, Bio 250, English 100})
Bio 250      >=   Max({Math 200, Bio 250, English 100})
English 100  >=   Max({Math 200, Bio 250, English 100})

因此,对于您的查询,它将始终只返回那些"拥有"平均工资"等于或大于"比最高的平均工资。下面是一个简单的版本,可以帮助您理解。

Drop Table #instructor 
Create Table #instructor (dept_name nvarchar(200), salary money)
Insert Into #instructor 
Select 'Math', 200
Union Select 'English', 150
Union Select 'Biology', 275
Union Select 'Computer Science', 300

select dept_name
from #instructor
group by dept_name
having avg (salary) >= all(select avg (salary)
                            from #instructor
                            group by dept_name)

您会注意到,在上面的示例中,显示的唯一部门是“计算机科学”。但如果你将生物学改为300,那么生物学和计算机科学都会出现。