在连接中重复使用别名

时间:2011-09-15 20:25:12

标签: sql sql-server tsql join

我正在尝试将使用COUNT(*)GROUP BY创建的列附加到计算的原始选择中。但是,选择非常复杂(远远超过我在示例中包含的WHERE ...行)所以我宁愿不复制代码。

SQL Server不支持在左连接语句中使用别名t1。有什么建议吗?


select t1.school, t1.grade,t1.individual,t2.cnt as 'class size' from (
        select * from students
        where (students.age < 16 and students.ACT_score is not null)
) as t1
left join (
    select distinct school, grade, count(*) as 'cnt' from t1
    group by school, grade
) as t2
on t1.school = t2.school and t1.grade = t2.grade

3 个答案:

答案 0 :(得分:3)

如果是2005年或更新版本,请使用CTE:

;WITH MyCTE AS
(
<Your complicate query here>
)
SELECT fields
FROM MyCTE
JOIN (subquery referencing MyCTE)
...

答案 1 :(得分:3)

如果将COUNT(*)与OVER子句一起使用,可能更容易维护,如下所示:

with cntAppended as (
  select
    *,
    count(*) over (partition by school, grade)
  from students
)
  select
    school, 
    grade,
    individual,
    cnt as "class size"
from cntAppended
where (age < 16 and ACT_score is not null)

不要试图避免使用WITH并将WHERE子句放在COUNT的一个查询中。如果你这样做,你将只计算每个学校和年级的学生&lt; 16,并有ACT分数。看起来您想要计算所有学生的[班级大小]列,但只能查看结果中某些学生的数据。

如果和当T-SQL supports the QUALIFY keyword时,这样的查询可能更容易:

select
  school, 
  grade,
  individual,
  count(*) over (partition by school, grade) as "class size"
from students
QUALIFY (age < 16 and ACT_score is not null)

答案 2 :(得分:1)

我以更简单的形式重写了您的查询,不需要CTE:

SELECT t1.school
    ,t1.grade
    ,t1.individual
    ,t2.cnt AS 'class size'
FROM students t1
LEFT JOIN (
    SELECT school
        ,grade
        ,count(*) AS 'cnt'
    FROM students 
    GROUP BY school, grade
) AS t2 ON t1.school = t2.school
        AND t1.grade = t2.grade
WHERE t1.age < 16
    AND t1.ACT_score IS NOT NULL