sql練習45題


sql練習45題

原文  ⚠️原文的解題答案有很多的錯誤,作者肯定沒有經過驗證,誤人子弟啊。

 
4個表的關系:
teacher-course-sc-student
 
 
自己驗證過的答案:https://github.com/chentianwei411/sql-45-
 

查詢問題

1.查詢" 01 "課程比" 02 "課程成績高的學生的信息及課程分數
1.1 查詢同時存在" 01 "課程和" 02 "課程的情況
1.2 查詢存在" 01 "課程但可能不存在" 02 "課程的情況(不存在時顯示為 null ) 1.3 查詢不存在" 01 "課程但存在" 02 "課程的情況
2.查詢平均成績大於等於 60 分的同學的學生編號和學生姓名和平均成績
3.查詢在 SC 表存在成績的學生信息
4.查詢所有同學的學生編號、學生姓名、選課總數、所有課程的總成績(沒成績的顯示為 null ) 4.1 查有成績的學生信息
5.查詢「李」姓老師的數量
6.查詢學過「張三」老師授課的同學的信息
7.查詢沒有學全所有課程的同學的信息
8.查詢至少有一門課與學號為" 01 "的同學所學相同的同學的信息
9.查詢和" 01 "號的同學學習的課程 完全相同的其他同學的信息
10.查詢沒學過"張三"老師講授的任一門課程的學生姓名
11.查詢兩門及其以上不及格課程的同學的學號,姓名及其平均成績
12.檢索" 01 "課程分數小於 60,按分數降序排列的學生信息
13.按平均成績從高到低顯示所有學生的所有課程的成績以及平均成績
14.查詢各科成績最高分、最低分和平均分: 以如下形式顯示:課程 ID,課程 name,最高分,最低分,平均分,及格率,中等率,優良率,優秀率 及格為>=60,中等為:70-80,優良為:80-90,優秀為:>=90 要求輸出課程號和選修人數,查詢結果按人數降序排列,若人數相同,按課程號升序排列
15.按各科成績進行排序,並顯示排名, Score 重復時保留名次空缺 15.1 按各科成績進行排序,並顯示排名, Score 重復時合並名次
16.查詢學生的總成績,並進行排名,總分重復時保留名次空缺 16.1 查詢學生的總成績,並進行排名,總分重復時不保留名次空缺
17.統計各科成績各分數段人數:課程編號,課程名稱,[100-85],[85-70],[70-60],[60-0] 及所占百分比
18.查詢各科成績前三名的記錄
19.查詢每門課程被選修的學生數
20.查詢出只選修兩門課程的學生學號和姓名
21.查詢男生、女生人數
22.查詢名字中含有「風」字的學生信息
23.查詢同名同性學生名單,並統計同名人數
24.查詢 1990 年出生的學生名單
25.查詢每門課程的平均成績,結果按平均成績降序排列,平均成績相同時,按課程編號升序排列
26.查詢平均成績大於等於 85 的所有學生的學號、姓名和平均成績
27.查詢課程名稱為「數學」,且分數低於 60 的學生姓名和分數
28.查詢所有學生的課程及分數情況(存在學生沒成績,沒選課的情況)
29.查詢任何一門課程成績在 70 分以上的姓名、課程名稱和分數
30.查詢不及格的課程
31.查詢課程編號為 01 且課程成績在 80 分以上的學生的學號和姓名
32.求每門課程的學生人數
33.假設成績不重復,查詢選修「張三」老師所授課程的學生中,成績最高的學生信息及其成績
34.假設成績有重復的情況下,查詢選修「張三」老師所授課程的學生中,成績最高的學生信息及其成績
35.查詢不同課程成績相同的學生的學生編號、課程編號、學生成績
36.查詢每門功成績最好的前兩名
37.統計每門課程的學生選修人數(超過 5 人的課程才統計)。
38.檢索至少選修兩門課程的學生學號
39.查詢選修了全部課程的學生信息
40.查詢各學生的年齡,只按年份來算
41.按照出生日期來算,當前月日 < 出生年月的月日則,年齡減一
42.查詢本周過生日的學生
43.查詢下周過生日的學生
44.查詢本月過生日的學生
45.查詢下月過生日的學生



針對16題:

MySQL 8.0窗口函數:用非常規思維簡易實現SQL需求

需要在單表中滿足某些條件的記錄集內部做一些函數操作,不是簡單的表連接,也不是簡單的聚合可以實現的,通常會讓寫SQL的同學焦頭爛額、絞盡腦汁,費了大半天時間寫出來一堆長長的晦澀難懂的自連接SQL,且性能低下,難以維護。

要解決此類問題,最方便的就是使用窗口函數。

 

MySQL從8.0開始支持窗口函數,分析函數

利用窗口函數解決排名問題:https://blog.csdn.net/qq_41080850/article/details/86310311

-- 16.查詢學生的總成績,並進行排名,總分重復時保留名次空缺
select sid, sum(score) from SC
group by sid
order by sum(score) desc  --沒有排名,所以對它進行一下排名。

  -- +------+-------+------+------------+
  -- | sid  | scos  | rn   | @sco:=scos |
  -- +------+-------+------+------------+
  -- | 01   | 269.0 | 1    |      269.0 |
  -- | 03   | 240.0 | 2    |      240.0 |
  -- | 02   | 210.0 | 3    |      210.0 |
  -- | 07   | 187.0 | 4    |      187.0 |
  -- | 05   | 163.0 | 5    |      163.0 |
  -- | 04   | 100.0 | 6    |      100.0 |
  -- | 06   |  65.0 | 7    |       65.0 |
  -- +------+-------+------+------------+
set @sco:=null,@rank=0;
select q.sid, scos,
case when @sco=scos then '' else @rank:=@rank+1 end as rn,
@sco:=scos
from(
    select sc.sid, sum(sc.score) as scos from sc
    group by sc.sid
    order by scos desc) q;
-- 16.1查詢學生的總成績,並進行排名,總分重復時不保留名次空缺 set @crank=0; select q.sid, total, @crank := @crank +1 as rn from( select sc.sid, sum(sc.score) as total from sc group by sc.sid order by total desc)q;

-- ⚠️ 也可以使用Mysql8.0版本的窗口函數。 -- 1.有重復排名使用 dense_rank(),假如有並列第3名的2個學生,那么再下一個學生的排名是第4名 select *, row_number() over (order by total desc) as rank1 from ( select sc.sid, sum(sc.score) as total from sc group by sc.sid) q; -- 2. 僅僅簡單的排序,忽略重復使用row_rank() -- 3.使用rank(), 即有重復排名,並且設置間隔,即假如有並列第3的2個學生,那么再下一個學生的排名是第5名。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM