如何在 WHERE 子句的 SELECT 子句中使用子查询的输出?
How can I use output of sub-query in SELECT clause in WHERE clause?
这是关于 SQL Server 2005 以后的。
如何在 WHERE
子句中使用 SELECT
子句中的子查询输出?
Student_Master
Student_Id Student_Name
1 A
2 B
3 C
Student_Details
Student_Id Student_Info
1 1_Info1
2 2_Info1
2 2_Info2
2 2_Info3
我想从 table Student_Master 和 COUNT(Student_Details.Student_Info) 中获取学生信息计数 > 0 的所有列。
预期输出:-
Student_Id Student_Name InfoCount
1 A 1
2 B 3
以下是不正确的语法,但为了解释我正在尝试做的事情:-
SELECT Student_Id, Student_Name,
(
SELECT COUNT(*) FROM Student_Details
WHERE Student_Master.Student_Id = Student_Details.Student_Id
) AS InfoCount
FROM Student_Master
WHERE InfoCount > 0
我知道以下 CORRECT 语法有效:-
SELECT Student_Id, Student_Name,
(
SELECT COUNT(*) FROM Student_Details
WHERE Student_Master.Student_Id = Student_Details.Student_Id
) AS InfoCount
FROM Student_Master
WHERE (
SELECT COUNT(*) FROM Student_Details
WHERE Student_Master.Student_Id = Student_Details.Student_Id
)> 0
但是在这里,我必须写两次相同的子查询。这个子查询将执行两次并且会影响性能。大师table有2500万条记录,详情table有1亿条记录。
索引和其他优化都可以,但我想首先编写最优化的查询。
如果您只是 Inner Join Student_Master
到 Student_Details
,您将只会获得具有 count > 0
的记录
SELECT Student_Id,
Student_Name,
COUNT(*) InfoCount
FROM Student_Master sm
JOIN Student_Details sd ON sm.Student_Id = sd.Student_Id
GROUP BY Student_Id,
Student_Name
如果出于某种原因您需要查找计数大于 1 的记录,那么您可以使用 Group By Having
SELECT Student_Id,
Student_Name,
COUNT(*) InfoCount
FROM Student_Master sm
JOIN Student_Details sd ON sm.Student_Id = sd.Student_Id
GROUP BY Student_Id,
Student_Name
HAVING COUNT(*) > 1
如果您想避免使用大型 Group by 语句,您可以在此处内联到子查询。
SELECT sm.Student_Id,
sm.Student_Name,
ic.InfoCount
FROM Student_Master sm
INNER JOIN (
SELECT Student_Id, COUNT(*) InfoCount
FROM Student_Details
GROUP BY Student_Id
) ic ON sm.Student_Id = ic.Student_Id
使用 APPLY 最简单且更容易编写的方法如下:
SELECT Student_Master.*, InfoCount
FROM Student_Master
OUTER APPLY (SELECT COUNT(*) InfoCount FROM Student_Details
WHERE Student_Details.Student_Id=Student_Master.Student_Id ) InfoCounts
WHERE InfoCount>0
这里也优化为查询计划如下:
这是关于 SQL Server 2005 以后的。
如何在 WHERE
子句中使用 SELECT
子句中的子查询输出?
Student_Master
Student_Id Student_Name
1 A
2 B
3 C
Student_Details
Student_Id Student_Info
1 1_Info1
2 2_Info1
2 2_Info2
2 2_Info3
我想从 table Student_Master 和 COUNT(Student_Details.Student_Info) 中获取学生信息计数 > 0 的所有列。
预期输出:-
Student_Id Student_Name InfoCount
1 A 1
2 B 3
以下是不正确的语法,但为了解释我正在尝试做的事情:-
SELECT Student_Id, Student_Name,
(
SELECT COUNT(*) FROM Student_Details
WHERE Student_Master.Student_Id = Student_Details.Student_Id
) AS InfoCount
FROM Student_Master
WHERE InfoCount > 0
我知道以下 CORRECT 语法有效:-
SELECT Student_Id, Student_Name,
(
SELECT COUNT(*) FROM Student_Details
WHERE Student_Master.Student_Id = Student_Details.Student_Id
) AS InfoCount
FROM Student_Master
WHERE (
SELECT COUNT(*) FROM Student_Details
WHERE Student_Master.Student_Id = Student_Details.Student_Id
)> 0
但是在这里,我必须写两次相同的子查询。这个子查询将执行两次并且会影响性能。大师table有2500万条记录,详情table有1亿条记录。
索引和其他优化都可以,但我想首先编写最优化的查询。
如果您只是 Inner Join Student_Master
到 Student_Details
,您将只会获得具有 count > 0
SELECT Student_Id,
Student_Name,
COUNT(*) InfoCount
FROM Student_Master sm
JOIN Student_Details sd ON sm.Student_Id = sd.Student_Id
GROUP BY Student_Id,
Student_Name
如果出于某种原因您需要查找计数大于 1 的记录,那么您可以使用 Group By Having
SELECT Student_Id,
Student_Name,
COUNT(*) InfoCount
FROM Student_Master sm
JOIN Student_Details sd ON sm.Student_Id = sd.Student_Id
GROUP BY Student_Id,
Student_Name
HAVING COUNT(*) > 1
如果您想避免使用大型 Group by 语句,您可以在此处内联到子查询。
SELECT sm.Student_Id,
sm.Student_Name,
ic.InfoCount
FROM Student_Master sm
INNER JOIN (
SELECT Student_Id, COUNT(*) InfoCount
FROM Student_Details
GROUP BY Student_Id
) ic ON sm.Student_Id = ic.Student_Id
使用 APPLY 最简单且更容易编写的方法如下:
SELECT Student_Master.*, InfoCount
FROM Student_Master
OUTER APPLY (SELECT COUNT(*) InfoCount FROM Student_Details
WHERE Student_Details.Student_Id=Student_Master.Student_Id ) InfoCounts
WHERE InfoCount>0
这里也优化为查询计划如下: