學生表/教師表/課程表/成績表常見SQL查詢
阿新 • • 發佈:2019-02-20
1. 在表中插入符合主鍵
[sql]
/*成績表*/
CREATE TABLE SC
(
Sid INT REFERENCES Student(Sid), /*學生學號*/
Cid INT REFERENCES Course(Cid), /*課程編號*/
Score INT NOT NULL, /*課程分數*/
PRIMARY KEY(Sid,Cid) /*將學生學號和課程編號設為複合主鍵*/
)
2. 查詢各科成績最高分,最低分以及平均分
[sql]
SELECT c.Cname, MAX(s.Score) AS Max, MIN(s.Score) AS Min, AVG(s.Score) AS Average
FROM Course c JOIN SC s ON c.Cid = s.Cid
GROUP BY c.Cname
/*此處應注意,若不按照c.Cname進行分組,SQL語句會報錯,c.Cname在SELECT語句中不合法,因為它
並未出現在聚合函式中也沒有出現在GROUP BY語句中*/
3. 查詢平均成績大於80分的學生姓名以及平均成績
[sql]
SELECT Sname, AVG(Score) AS Average FROM Student JOIN SC
ON Student.Sid=SC.Sid
GROUP BY Sname
HAVING AVG(Score)>80
/*以聚合函式為條件進行刪選只能在HAVING語句中進行,WHERE語句不支援聚合函式*/
4. 查詢各學生都選了多少門課
[sql]
SELECT Sname, COUNT(Cid) AS TOTAL_COURSE FROM Student
LEFT JOIN SC ON Student.Sid=SC.Sid
GROUP BY Sname
/*使用LEFT JOIN可以將一門課也沒有選的學生也查詢出來,
若不加LEFT查不出DAISY和SHERRY*/
5. 查詢沒有選JANE老師課的學生資訊
[sql]
SELECT s.Sid,s.Sname,s.Sage,s.Sage FROM Student s
WHERE s.Sid NOT IN
(SELECT s.Sid FROM SC s JOIN Course c ON s.Cid=c.Cid
JOIN Teacher t ON c.Tid=t.Tid
WHERE t.Tname='JANE')
/*子查詢中查詢出所有選擇JANE老師課的學生學號,
主查詢去查詢在學生表中但不在子查詢結果集中的學生資訊*/
6. 查詢既選擇了COMPUTER課程,又選擇了MATH課程的學生資訊
[sql]
SELECT s.Sid,s.Sname,s.Sage,s.Ssex FROM STUDENT s
JOIN SC ss ON s.Sid=ss.Sid
JOIN Course c ON ss.Cid=c.Cid WHERE c.Cname='COMPUTER'
INTERSECT
SELECT s.Sid,s.Sname,s.Sage,s.Ssex FROM STUDENT s
JOIN SC ss ON s.Sid=ss.Sid
JOIN Course c ON ss.Cid=c.Cid WHERE c.Cname='MATH'
/*第一個查詢查詢出選擇COMPUTER課程的學生資訊,
第二個查詢查詢出選擇MATH課程的學生資訊,
用INTERSECT關鍵字取交集*/
7. 查詢COMPUTER課程比MATH課程分數高的學生學號
[sql]
SELECT a.Sid FROM
(SELECT s.Sid,s.Score FROM SC s JOIN Course c ON s.Cid=c.Cid WHERE c.Cname='COMPUTER') a
JOIN
(SELECT s.Sid,s.Score FROM SC s JOIN Course c ON s.Cid=c.Cid WHERE c.Cname='MATH') b
ON a.Sid=b.Sid
WHERE a.Score>b.Score
/*將選了COMPUTER課的學生學號和成績和選了MATH課的學生學號和成績連線
WHERE語句限制COMPUTER課的成績高於MATH課*/
8. 查詢和JOHN選的課相同的學生資訊
[sql]
SELECT Student.Sname FROM Student JOIN SC ON Student.Sid=SC.Sid
WHERE SC.Cid IN
(SELECT SC.Cid FROM SC JOIN Student ON SC.Sid=Student.Sid WHERE Student.Sname='JOHN') /*查詢選了的課JOHN也都選了的學生的姓名*/
AND Student.Sname<>'JOHN' /*限制該學生不能是JOHN本人*/
GROUP BY Student.Sname
HAVING COUNT(SC.Cid)=
(SELECT COUNT(*) FROM SC JOIN Student ON SC.Sid=Student.Sid WHERE Student.Sname='JOHN') /*該學生選的課程總數與JOHN選的課程總數相同*/
9. 按總分為學生排名,總分相同名次相同
[sql]
SELECT RANK() OVER (ORDER BY SUM(ss.Score) DESC) AS Rank, s.Sname, ISNULL(SUM(ss.Score),0)
FROM Student s LEFT JOIN SC ss
ON s.Sid = ss.Sid
GROUP BY s.Sname
ORDER BY SUM(ss.Score) DESC
/*RANK()是SQL Server的一個built-in函式,語法為
RANK() OVER ( [ partition_by_clause ] order_by_clause ).*/
10. 查詢總分在100至200之間的學生姓名及總分
[sql]
SELECT s.Sname,SUM(ss.Score) FROM Student s JOIN SC ss ON s.Sid=ss.Sid
GROUP BY s.Sname HAVING SUM(ss.Score) BETWEEN 100 AND 200
11. 查詢總分第六到十名的學生姓名以及總分
[sql]
SELECT * FROM
(SELECT TOP(5) * FROM
(SELECT TOP(10) SC.Sid,SUM(SC.Score) AS SUM FROM SC GROUP BY SC.Sid ORDER BY SUM(SC.Score)) a
ORDER BY a.SUM) b
ORDER BY b.SUM DESC
/*SELECT TOP(10) SC.Sid,SUM(SC.Score) AS SUM FROM SC GROUP BY SC.Sid ORDER BY SUM(SC.Score)查詢出總分前十名
SELECT TOP(5) FROM (...) a ORDER BY a.SUM查詢出成績六到十名
SELECT * FROM (...) b ORDER BY b.SUM DESC將結果倒序按照從高分到低分排列*/
12. 查詢各科成績的前三名以及分數
[sql]
SELECT s.Sid,s.Cid,s.Score FROM SC s
WHERE s.Score IN
(SELECT TOP(3) Score FROM SC WHERE s.Cid= Cid ORDER BY score DESC)
ORDER BY s.Cid;
/*從SC表中查詢出學生學號,課程編號以及成績,WHERE子句限制了查詢出的記錄成績必須在子查詢集合內
子查詢查詢出了各科成績的前三名並通過課程編號和主查詢關聯*/
13. 查詢有不及格科目的學生的姓名,不及格科目以及不及格科目成績
[sql]
SELECT s.Sname,c.Cname,ss.Score FROM Student s JOIN SC ss ON s.Sid=ss.Sid JOIN Course c ON ss.Cid=c.Cid
WHERE ss.Score<60
14. 查詢所有學生都選修的課程
[sql]
SELECT c.Cname FROM SC s JOIN Course c ON s.Cid=c.Cid
GROUP BY c.Cname HAVING COUNT(s.Sid)=(SELECT COUNT(*) FROM Student)
15. 查詢選修了兩門或以上的學生姓名及選修總科目
[sql]
SELECT s.Sname,COUNT(ss.Cid) AS TOTAL FROM Student s JOIN SC ss ON s.Sid=ss.Sid
GROUP BY s.Sname HAVING COUNT(ss.Cid)>1
[sql]
/*成績表*/
CREATE TABLE SC
(
Sid INT REFERENCES Student(Sid), /*學生學號*/
Cid INT REFERENCES Course(Cid), /*課程編號*/
Score INT NOT NULL, /*課程分數*/
PRIMARY KEY(Sid,Cid) /*將學生學號和課程編號設為複合主鍵*/
)
2. 查詢各科成績最高分,最低分以及平均分
[sql]
SELECT c.Cname, MAX(s.Score) AS Max, MIN(s.Score) AS Min, AVG(s.Score) AS Average
FROM Course c JOIN SC s ON c.Cid = s.Cid
GROUP BY c.Cname
/*此處應注意,若不按照c.Cname進行分組,SQL語句會報錯,c.Cname在SELECT語句中不合法,因為它
並未出現在聚合函式中也沒有出現在GROUP BY語句中*/
3. 查詢平均成績大於80分的學生姓名以及平均成績
[sql]
SELECT Sname, AVG(Score) AS Average FROM Student JOIN SC
ON Student.Sid=SC.Sid
GROUP BY Sname
HAVING AVG(Score)>80
/*以聚合函式為條件進行刪選只能在HAVING語句中進行,WHERE語句不支援聚合函式*/
4. 查詢各學生都選了多少門課
[sql]
SELECT Sname, COUNT(Cid) AS TOTAL_COURSE FROM Student
LEFT JOIN SC ON Student.Sid=SC.Sid
GROUP BY Sname
/*使用LEFT JOIN可以將一門課也沒有選的學生也查詢出來,
若不加LEFT查不出DAISY和SHERRY*/
5. 查詢沒有選JANE老師課的學生資訊
[sql]
SELECT s.Sid,s.Sname,s.Sage,s.Sage FROM Student s
WHERE s.Sid NOT IN
(SELECT s.Sid FROM SC s JOIN Course c ON s.Cid=c.Cid
JOIN Teacher t ON c.Tid=t.Tid
WHERE t.Tname='JANE')
/*子查詢中查詢出所有選擇JANE老師課的學生學號,
主查詢去查詢在學生表中但不在子查詢結果集中的學生資訊*/
6. 查詢既選擇了COMPUTER課程,又選擇了MATH課程的學生資訊
[sql]
SELECT s.Sid,s.Sname,s.Sage,s.Ssex FROM STUDENT s
JOIN SC ss ON s.Sid=ss.Sid
JOIN Course c ON ss.Cid=c.Cid WHERE c.Cname='COMPUTER'
INTERSECT
SELECT s.Sid,s.Sname,s.Sage,s.Ssex FROM STUDENT s
JOIN SC ss ON s.Sid=ss.Sid
JOIN Course c ON ss.Cid=c.Cid WHERE c.Cname='MATH'
/*第一個查詢查詢出選擇COMPUTER課程的學生資訊,
第二個查詢查詢出選擇MATH課程的學生資訊,
用INTERSECT關鍵字取交集*/
7. 查詢COMPUTER課程比MATH課程分數高的學生學號
[sql]
SELECT a.Sid FROM
(SELECT s.Sid,s.Score FROM SC s JOIN Course c ON s.Cid=c.Cid WHERE c.Cname='COMPUTER') a
JOIN
(SELECT s.Sid,s.Score FROM SC s JOIN Course c ON s.Cid=c.Cid WHERE c.Cname='MATH') b
ON a.Sid=b.Sid
WHERE a.Score>b.Score
/*將選了COMPUTER課的學生學號和成績和選了MATH課的學生學號和成績連線
WHERE語句限制COMPUTER課的成績高於MATH課*/
8. 查詢和JOHN選的課相同的學生資訊
[sql]
SELECT Student.Sname FROM Student JOIN SC ON Student.Sid=SC.Sid
WHERE SC.Cid IN
(SELECT SC.Cid FROM SC JOIN Student ON SC.Sid=Student.Sid WHERE Student.Sname='JOHN') /*查詢選了的課JOHN也都選了的學生的姓名*/
AND Student.Sname<>'JOHN' /*限制該學生不能是JOHN本人*/
GROUP BY Student.Sname
HAVING COUNT(SC.Cid)=
(SELECT COUNT(*) FROM SC JOIN Student ON SC.Sid=Student.Sid WHERE Student.Sname='JOHN') /*該學生選的課程總數與JOHN選的課程總數相同*/
9. 按總分為學生排名,總分相同名次相同
[sql]
SELECT RANK() OVER (ORDER BY SUM(ss.Score) DESC) AS Rank, s.Sname, ISNULL(SUM(ss.Score),0)
FROM Student s LEFT JOIN SC ss
ON s.Sid = ss.Sid
GROUP BY s.Sname
ORDER BY SUM(ss.Score) DESC
/*RANK()是SQL Server的一個built-in函式,語法為
RANK() OVER ( [ partition_by_clause ] order_by_clause ).*/
10. 查詢總分在100至200之間的學生姓名及總分
[sql]
SELECT s.Sname,SUM(ss.Score) FROM Student s JOIN SC ss ON s.Sid=ss.Sid
GROUP BY s.Sname HAVING SUM(ss.Score) BETWEEN 100 AND 200
11. 查詢總分第六到十名的學生姓名以及總分
[sql]
SELECT * FROM
(SELECT TOP(5) * FROM
(SELECT TOP(10) SC.Sid,SUM(SC.Score) AS SUM FROM SC GROUP BY SC.Sid ORDER BY SUM(SC.Score)) a
ORDER BY a.SUM) b
ORDER BY b.SUM DESC
/*SELECT TOP(10) SC.Sid,SUM(SC.Score) AS SUM FROM SC GROUP BY SC.Sid ORDER BY SUM(SC.Score)查詢出總分前十名
SELECT TOP(5) FROM (...) a ORDER BY a.SUM查詢出成績六到十名
SELECT * FROM (...) b ORDER BY b.SUM DESC將結果倒序按照從高分到低分排列*/
12. 查詢各科成績的前三名以及分數
[sql]
SELECT s.Sid,s.Cid,s.Score FROM SC s
WHERE s.Score IN
(SELECT TOP(3) Score FROM SC WHERE s.Cid= Cid ORDER BY score DESC)
ORDER BY s.Cid;
/*從SC表中查詢出學生學號,課程編號以及成績,WHERE子句限制了查詢出的記錄成績必須在子查詢集合內
子查詢查詢出了各科成績的前三名並通過課程編號和主查詢關聯*/
13. 查詢有不及格科目的學生的姓名,不及格科目以及不及格科目成績
[sql]
SELECT s.Sname,c.Cname,ss.Score FROM Student s JOIN SC ss ON s.Sid=ss.Sid JOIN Course c ON ss.Cid=c.Cid
WHERE ss.Score<60
14. 查詢所有學生都選修的課程
[sql]
SELECT c.Cname FROM SC s JOIN Course c ON s.Cid=c.Cid
GROUP BY c.Cname HAVING COUNT(s.Sid)=(SELECT COUNT(*) FROM Student)
15. 查詢選修了兩門或以上的學生姓名及選修總科目
[sql]
SELECT s.Sname,COUNT(ss.Cid) AS TOTAL FROM Student s JOIN SC ss ON s.Sid=ss.Sid
GROUP BY s.Sname HAVING COUNT(ss.Cid)>1