做數據sql不熟練?解析50道經典面試題,sql從入門到進階

2021-02-16 程式設計師阿狗

明天要面試,十萬火急!!!

數據下午出,火燒眉毛了!!!

阿狗怎麼辦???

遇到事情不要慌,打開題庫刷一刷。

給大家整理了流傳已久的50道sql面試經典題目,解題思路和SQL答案一併附上,難度循序漸進,考察點非常全面,自己刷完這些題目後基本可以應對大部分面試題目和工作場景。工作之餘也可以拿出來練練手,對知識點查缺補漏。

題目背景:資料庫中有四張表,全部題目以四張表為基礎,欄位如下:

複習下建表和插入數據的語句(可以自己在navicat中練習):

create table Student(SId varchar(10),Sname varchar(10),Sage datetime,Ssex varchar(10));insert into Student values('01' , '趙雷' , '1990-01-01' , '男');insert into Student values('02' , '錢電' , '1990-12-21' , '男');insert into Student values('03' , '孫風' , '1990-12-20' , '男');insert into Student values('04' , '李雲' , '1990-12-06' , '男');insert into Student values('05' , '周梅' , '1991-12-01' , '女');insert into Student values('06' , '吳蘭' , '1992-01-01' , '女');insert into Student values('07' , '鄭竹' , '1989-01-01' , '女');insert into Student values('09' , '張三' , '2017-12-20' , '女');insert into Student values('10' , '李四' , '2017-12-25' , '女');insert into Student values('11' , '李四' , '2012-06-06' , '女');insert into Student values('12' , '趙六' , '2013-06-13' , '女');insert into Student values('13' , '孫七' , '2014-06-01' , '女');

create table Course(CId varchar(10),Cname nvarchar(10),TId varchar(10));insert into Course values('01' , '語文' , '02');insert into Course values('02' , '數學' , '01');insert into Course values('03' , '英語' , '03');

create table Teacher(TId varchar(10),Tname varchar(10));insert into Teacher values('01' , '張三');insert into Teacher values('02' , '李四');insert into Teacher values('03' , '王五');

create table SC(SId varchar(10),CId varchar(10),score decimal(18,1));insert into SC values('01' , '01' , 80);insert into SC values('01' , '02' , 90);insert into SC values('01' , '03' , 99);insert into SC values('02' , '01' , 70);insert into SC values('02' , '02' , 60);insert into SC values('02' , '03' , 80);insert into SC values('03' , '01' , 80);insert into SC values('03' , '02' , 80);insert into SC values('03' , '03' , 80);insert into SC values('04' , '01' , 50);insert into SC values('04' , '02' , 30);insert into SC values('04' , '03' , 20);insert into SC values('05' , '01' , 76);insert into SC values('05' , '02' , 87);insert into SC values('06' , '01' , 31);insert into SC values('06' , '03' , 34);insert into SC values('07' , '02' , 89);insert into SC values('07' , '03' , 98);

建好表後第一件事要先把幾張表的關聯關係理清楚,然後再來看題目。這是網友做的關係圖:

題目:

1. 查詢" 01 "課程比" 02 "課程成績高的學生的信息及課程分數

思路:關聯每名學生的兩門課程成績,再選出01課程比02課程高的學生

select s.*, sc1.score, sc2.scorefrom Student sleft join (select SId, score from SC where CId = '01') sc1 on s.SId = sc1.SIdleft join (select SId, score from SC where CId = '02') sc2on s.SId = sc2.SIdwhere sc1.score > sc2.score

2. 查詢平均成績大於等於 60 分的同學的學生編號和學生姓名和平均成績

思路:在成績表中分組計算平均分,再關聯學生表

select s.*, r.Sname from (select SId, avg(score) as sfrom sc group by SIdhaving avg(scoare) >= 60) rleft join Student st on r.SId = st.SId

3. 查詢在 SC 表存在成績的學生信息

select distinct s.*from Student s, scwhere s.SId = sc.SId

4. 查詢所有同學的學生編號、學生姓名、選課總數、所有課程的成績總和

思路:涉及所有同學的所有課程,Student表 join SC表

select s.SId, s.Sname, count(SC.CId), sum(SC.score)from Student sjoin SC on s.SId=  SC.SIdgroup by s.SId, s.Sname

5. 查詢「李」姓老師的數量

select count(*)from Teacher where Tname like '李%'

6. 查詢學過「張三」老師授課的同學的信息

思路:多表聯合查詢

select distinct s.*from Student s, Teacher t, SC, Course cwhere s.SId = SC.SId and SC.CId = c.CId and c.TId = t.Tid and T.Tname = '張三'order by s.SId

7. 查詢沒有學全所有課程的同學的信息

思路:統計學生課程數小於課程表裡的課程數

select s.SId, s.Sname, count(SC.CId)from Student s inner join SC on s.SId=  SC.SIdgroup by s.SId, s.Sname having count(SC.CId) < (select count(distinct CId) from Course)

8. 查詢至少有一門課與學號為" 01 "的同學所學相同的同學的信息

思路:找出01同學上過的課程,統計SC表中在這些課程中的SId

select s.*from Student s, SC where s.SId = SC.SId and SC.CId in (select CId from SC where SId = '01')and s.SId <> '01'

9. 查詢和" 01 "號的同學學習的課程完全相同的其他同學的信息(較難)

思路:group_concat函數

select s.*from Student s where s.SId in (select sid from sc where sid<>'01' group by sidhaving group_concat(CId order by CId) = (select group_concat(CId order by CId) from SC where sid = '01'))

10. 查詢沒學過"張三"老師講授的任一門課程的學生姓名

思路:三重嵌套,張三老師的課->上過課的學生->不在這個集合中的學生

select s.* from Student where s.SId not in (select SId from SC where SC.CId in (select c.CIdfrom Teacher t, Course c where t.TId = c.TId and t.Tname = '張三'))

11. 查詢兩門及其以上不及格課程的同學的學號,姓名及其平均成績

思路:SC表中分組找到兩門及以上不及格的學生,再關聯他的平均成績

select s.SId, s.Sname, avg(SC.Score)from Student s, SC where s.SId = SC.SId and SC.SId in (select SId from SC where score < 60 group by SId having Count(1) >= 2)group by s.SId, s.Sname

12. 檢索" 01 "課程分數小於 60,按分數降序排列的學生信息

select s.SId, s.Sname, SC.score from SC, Student swhere SC.SId = s.SId and SC.score < 60 and SC.CId = '01'order by SC.score desc

13. 按平均成績從高到低顯示所有學生的所有課程的成績以及平均成績

SELECT S.Sid, B.平均成績, SUM(CASE WHEN Cid = '01' THEN Score ELSE NULL END) AS 成績01, SUM(CASE WHEN Cid = '02' THEN Score ELSE NULL END) AS 成績02, SUM(CASE WHEN Cid = '03' THEN Score ELSE NULL END) AS 成績03 FROM SC INNER JOIN (SELECT Sid, AVG(score) AS 平均成績 FROM SC GROUP BY Sid) AS B ON B.Sid = SC.Sid RIGHT OUTER JOIN Student AS S ON S.Sid = SC.Sid GROUP BY S.Sid, B.平均成績 ORDER BY B.平均成績 DESC NULLS LAST

14. 查詢各科成績最高分、最低分和平均分:

以如下形式顯示:

課程 ID,課程 name,最高分,最低分,平均分,及格率,中等率,優良率,優秀率(及格為>=60,中等為:70-80,優良為:80-90,優秀為:>=90)

要求:輸出課程號和選修人數,查詢結果按人數降序排列,若人數相同,按課程號升序排列。

select sc.CId ,max(sc.score)as 最高分,min(sc.score)as 最低分,AVG(sc.score)as 平均分,count(*)as 選修人數,sum(case when sc.score>=60 then 1 else 0 end )/count(*)as 及格率,sum(case when sc.score>=70 and sc.score<80 then 1 else 0 end )/count(*)as 中等率,sum(case when sc.score>=80 and sc.score<90 then 1 else 0 end )/count(*)as 優良率,sum(case when sc.score>=90 then 1 else 0 end )/count(*)as 優秀率 from scGROUP BY sc.CIdORDER BY count(*)DESC, sc.CId ASC

15. 按各科成績進行排序,並顯示排名, Score 重複時保留名次空缺

SELECT Sid, Cid, Score, RANK() OVER (PARTITION BY Cid ORDER BY Score DESC) AS ranking FROM SC

16. 查詢學生的總成績,並進行排名,總分重複時不保留名次空缺

SELECT Sid, SUM(Score), RANK () OVER (ORDER BY SUM(Score) DESC) AS ranking FROM SC GROUP BY Sid

17. 統計各科成績各分數段人數:課程編號,課程名稱,[100-85],[85-70],[70-60],[60-0] 及所佔百分比。

        SELECT Cid, COUNT(*) AS 選課人數, SUM(CASE WHEN Score>= 85 THEN 1 ELSE 0 END) * 100 / COUNT(*) AS 分數85_100比例, SUM(CASE WHEN Score BETWEEN  70 AND 85 THEN 1 ELSE 0 END) * 100 / COUNT(*) AS 分數70_85比例, SUM(CASE WHEN Score BETWEEN  60 AND 70 THEN 1 ELSE 0 END) * 100 / COUNT(*) AS 分數60_70比例, SUM(CASE WHEN Score BETWEEN  0 AND 60 THEN 1 ELSE 0 END) * 100 / COUNT(*) AS 分數0_60比例 FROM SC GROUP BY Cid

18. 查詢各科成績前三名的記錄

SELECT *FROM( SELECT Sid, Cid, Score, RANK() OVER (PARTITION BY Cid ORDER BY Score DESC) AS ranking FROM SC GROUP BY Sid, Cid) AS A WHERE A.ranking IN (1, 2, 3);

19. 查詢每門課程被選修的學生數

select cid, count(sid) from sc group by cid

20. 查詢出只選修兩門課程的學生學號和姓名

select student.sid, student.sname from studentwhere student.sid in(select sc.sid from scgroup by sc.sidhaving count(sc.cid)=2)

21. 查詢男生、女生人數

select Ssex, count(*) from studentgroup by Ssex

22. 查詢名字中含有「風」字的學生信息

select *from student where student.Sname like '%風%'

23. 查詢同名學生名單,並統計同名人數

select sname, count(*) from studentgroup by snamehaving count(*)>1

24. 查詢 1990 年出生的學生名單

select *from studentwhere YEAR(student.Sage)=1990

25. 查詢每門課程的平均成績,結果按平均成績降序排列,平均成績相同時,按課程編號升序排列

select sc.cid, course.cname, AVG(SC.SCORE) as average from sc, coursewhere sc.cid = course.cidgroup by sc.cid order by average desc,cid asc

26. 查詢平均成績大於等於 85 的所有學生的學號、姓名和平均成績

select student.sid, student.sname, AVG(sc.score) as aver from student, scwhere student.sid = sc.sidgroup by sc.sidhaving aver > 85

27. 查詢課程名稱為「數學」,且分數低於 60 的學生姓名和分數

select student.sname, sc.score from student, sc, coursewhere student.sid = sc.sidand course.cid = sc.cidand course.cname = "數學"and sc.score < 60

28. 查詢所有學生的課程及分數情況(存在學生沒成績,沒選課的情況)

select student.sname, cid, score from studentleft join scon student.sid = sc.sid;

29. 查詢任何一門課程成績在 70 分以上的姓名、課程名稱和分數

select student.sname, course.cname,sc.score from student,course,scwhere sc.score>70and student.sid = sc.sidand sc.cid = course.cid

30. 查詢存在不及格的課程

select cid from scwhere score< 60group by cid

31. 查詢課程編號為 01 且課程成績在 80 分及以上的學生的學號和姓名

select student.sid,student.sname from student,scwhere cid= '01'and score>=80and student.sid = sc.sid

32. 求每門課程的學生人數

select sc.CId,count(*) as 學生人數from scGROUP BY sc.CId

33. 成績不重複,查詢選修「張三」老師所授課程的學生中,成績最高的學生信息及其成績

select student.*, sc.score, sc.cid from student, teacher, course,sc where teacher.tid = course.tidand sc.sid = student.sidand sc.cid = course.cidand teacher.tname = "張三"order by score desclimit 1

34. 成績有重複的情況下,查詢選修「張三」老師所授課程的學生中,成績最高的學生信息及其成績

select student.*, sc.score, sc.cid from student, teacher, course,sc where teacher.tid = course.tidand sc.sid = student.sidand sc.cid = course.cidand teacher.tname = '張三'and sc.score = (select Max(sc.score) from sc,student, teacher, coursewhere teacher.tid = course.tidand sc.sid = student.sidand sc.cid = course.cidand teacher.tname = '張三')

35. 查詢不同課程成績相同的學生的學生編號、課程編號、學生成績

select  a.cid, a.sid,  a.score from sc as ainner join sc as bon a.sid = b.sidand a.cid != b.cidand a.score = b.scoregroup by cid, sid

36. 查詢每門功成績最好的前兩名

select a.sid,a.cid,a.score from sc as a left join sc as b on a.cid = b.cid and a.score<b.scoregroup by a.cid, a.sidhaving count(b.cid)<2order by a.cid

37. 統計每門課程的學生選修人數(超過 5 人的課程才統計)

select sc.cid, count(sid) as cc from scgroup by cidhaving cc > 5

38. 檢索至少選修兩門課程的學生學號

select sid, count(cid) as cc from scgroup by sidhaving cc>=2

39. 查詢選修了全部課程的學生信息

select student.*from sc ,student where sc.SId=student.SIdGROUP BY sc.SIdHAVING count(*) = (select DISTINCT count(*) from course )

40. 查詢各學生的年齡,只按年份來算

SELECT Sid, Sname, Sage,EXTRACT(YEAR FROM CURRENT_TIMESTAMP) - EXTRACT(YEAR FROM Sage) AS 年齡FROM Student

41. 接上一題按照出生日期來算,當前月日 < 出生年月的月日,則年齡減一

select student.SId as 學生編號,student.Sname  as  學生姓名,TIMESTAMPDIFF(YEAR,student.Sage,CURDATE()) as 學生年齡from student

42. 查詢本周過生日的學生

select *from student where WEEKOFYEAR(student.Sage)=WEEKOFYEAR(CURDATE())

43. 查詢下周過生日的學生

select *from student where WEEKOFYEAR(student.Sage)=WEEKOFYEAR(CURDATE())+1

44. 查詢本月過生日的學生

select *from student where MONTH(student.Sage)=MONTH(CURDATE())

45. 查詢下月過生日的學生

select *from student where MONTH(student.Sage)=MONTH(CURDATE())+1

46. 查詢同時存在" 01 「課程和」 02 "課程的情況

SELECT C1.sid, C3.sname, C3.sage, C3.ssex, C1.score AS score1, C2.score AS score2 FROM (SELECT * FROM SC WHERE Cid = '01') AS C1 INNER JOIN (SELECT * FROM SC WHERE Cid = '02') AS C2 ON C1.sid = C2.sid INNER JOIN Student AS C3 ON C1.sid = C3.sid WHERE C1.score <> C2.score OR C1.score = C2.score

47. 查詢存在" 01 「課程但可能不存在」 02 「課程的情況 (不存在時顯示為null)

SELECT C1.sid, C3.sname, C3.sage, C3.ssex, C1.score AS score1, COALESCE(CAST(C2.score AS VARCHAR(4)), 'NULL') AS score2 FROM (SELECT * FROM SC WHERE Cid = '01') AS C1 LEFT JOIN (SELECT * FROM SC WHERE Cid = '02') AS C2 ON C1.sid = C2.sid INNER JOIN Student AS C3 ON C1.sid = C3.sid

48. 查詢不存在" 01 「課程但存在」 02 "課程的情況

SELECT C2.sid, C3.sname, C3.sage, C3.ssex, C1.score AS score1, C2.score AS score2 FROM (SELECT * FROM SC WHERE Cid = '01') AS C1 RIGHT JOIN (SELECT * FROM SC WHERE Cid = '02') AS C2 ON C1.sid = C2.sid INNER JOIN Student AS C3 ON C2.sid = C3.sid WHERE C1.score IS NULL

49. 查有成績的學生信息

select * from studentwhere student.sid in (select sc.sid from sc)

50. 按各科成績進行排序,並顯示排名, Score 重複時合併名次

SELECT Sid, Cid, Score, DENSE_RANK() OVER (PARTITION BY Cid ORDER BY Score DESC) AS dense_ranking FROM SC

針對這50道經典題目,有B站up主專門製作了講解視頻,連結也一起附上:

https://www.bilibili.com/video/BV1q4411G7Lw/?p=4

喜歡的同學記得點下【收藏】和【在看】哦!

相關焦點

  • 如何學習SQL語言
    很多人喜歡一上來就推薦好幾本書,但是這些書晦澀難懂,對於初學者入門非常不友好。入門只需要一本書就夠了,而不是多本。
  • SparkSQL 50道練習題
    以夢為馬,不負韶華!\\BigData\\05-Spark\\0417\\4.16號練習題50道2.0\\data\\student.txt")   val rdd2: RDD[String] = sc.textFile("E:\\2020大數據新學年\\BigData\\05-Spark\\0417\\4.16號練習題50道2.0\\data\\course.txt")   val rdd3: RDD
  • 大數據分析工程師入門9-Spark SQL
    本文為《大數據分析師入門課程》系列的第9篇,在本系列的第8篇-Spark基礎中,已經對Spark做了一個入門介紹,在此基礎上本篇拎出Spark SQL,主要站在使用者的角度來進行講解,需要注意的是本文中的例子的代碼均使用Scala語言。
  • 手撕SQL | 必知必會5道SQL面試題
    愛數據曉輝 | 作者愛數據學院8月SQL月考題 | 來源附本次sql請根據各小題的需求,用代碼實現>表列名含義如下:name:國家名稱continent :該國家屬於哪個洲area:⾯積population:⼈⼝gdp:國內⽣產總值請用sql
  • sql子查詢面試題
    這是《從零學會sql》系列課程第4節課《複雜查詢》的練習題,也是常考常考的面試題。
  • SQL經典面試50題 | 附答案
    今天給大家分享一份星友對SQL經典面試50題的刷題記錄,寶器稍作了一些修改,以下是星友自述正文:看完了SQL基礎教程,然後再看SQL進階教程感覺有些不是很懂,於是就開始刷題熟悉⼀下基礎知識,找了⽐較經典的很多⼈都刷過的SQL⾯試50題,B站也有挺好的視頻解答,看題先⾃⼰做,不會就看視頻解答,感覺難題都在前⾯。
  • 大數據分析工程師面試集錦3-SQL/SparkSql/HiveQL
    大數據分析工程師80%的時間都在與SQL打交道,通過SQL完成業務方的各種臨時性需求分析和常規性報表統計。熟練的SQL技能能夠大大提高工作效率。本文將SQL/SparkSql/HiveQL放在一起來梳理一份常見題型的面試題庫。
  • 面試被問:JDBC底層是如何連接資料庫的?|sql|mysql|數據源|java|...
    背景  前兩天一個小夥伴面試的時候,被問JDBC底層是如何連接資料庫的?  他頓時一臉懵逼,因為大部分人只知道JDBC的幾個步驟,至於底層到底是怎麼連接資料庫的,還真不知道。  由於小夥伴是面試高級開發,問這種問題倒也不能說面試官過分,如果是初級或者中級,那問著問題就確實有些過分了。
  • 算法人必懂的進階SQL知識,4道面試常考題
    (圖片付費下載自視覺中國)作者 | 石曉文來源|小小挖掘機(ID:wAlsjwj)近期在不同群裡有小夥伴們提出了一些在面試和筆試中遇到的Hive SQL問題,Hive作為算法工程師的一項必備技能,在面試中也是極有可能被問到的,所以有備無患,本文將對這四道題進行詳細的解析
  • 50道SQL經典面試題(下)
    由於篇幅較長,上次已經給小夥伴們分享了25道面試題,還沒看的可以戳這裡:50道SQL經典面試題(上)今天繼續給小夥伴們補上剩下的25道。為便於閱讀理解,我們還是把表結構和測試數據給大家補上。VARCHAR (10),  Sname nvarchar (10),  Sage datetime,  Ssex nvarchar (10))--插入測試數據
  • 這些SQL技能你都會嗎? 經典SQL面試題送給你(附答案)
    儘管面試官虐我千百遍,我還待他如初戀。
  • 面試官經常喜歡問的Mybatis經典面試題,值得好好收藏哦!
    今天給大家分享一些面試官喜歡提問的Mybatis面試題,好了,廢話不多說,直接上乾貨吧!一、請說說在Mybatis 中#和$有什麼區別?#相當於對數據 加上 雙引號,$相當於直接顯示數據1.#將傳入的數據都當成一個字符串,會對自動傳入的數據加一個雙引號。如:order by #user_id#,如果傳入的值是111,那麼解析成 sql 時的值為 order by "111", 如果傳入的值是 id,則解析成的 sql 為 order by "id".2. $將傳入的數據直接顯示生成在 sql 中。
  • 當pandas撞上了sql,於是一個強大的pandasql庫產生了!
    演示數據本文的所有演示數據,均是基於下方的四張表。下面這四張表大家應該不陌生,這就是網傳50道經典MySQL面試題中使用到的幾張原表。關於下方各表之間的關聯關係,我就不給大家說明了,仔細觀察欄位名,應該就可以發現。
  • 一道簡單的sql語句題
    這是很早之前面的,第一次面數據分析的面試,當時還傻乎乎的以為數據分析和數據挖掘是一回事呢。
  • 適用於初學者和分析師的SQL –使用Python入門SQL
    SQL是每個分析師和數據科學家都應該知道的語言。沒有逃避這個。在您的分析或數據科學面試回合中,您會遇到很多SQL問題,特別是如果您是該領域的新手。如果您最近一直在推遲學習SQL,那麼現在該採取行動並開始動手了。您將必須了解資料庫以處理數據,所以為什麼不立即開始您的SQL旅程呢?我個人使用SQL已經有一段時間了,可以證明它的用處,尤其是在這些黃金數據驅動的時代。
  • 幾道常見的SQL面試題,看你能答對幾道?
    SQL面試題,在不看底部參考答案的情況下,看自己能做對幾道。查成這樣一個結果6.說明:拷貝表( 拷貝數據, 源表名:a目標表名:b) 8. 說明:顯示文章、提交人和最後回復時間 9. 說明:外連接查詢( 表名1 :a表名2 :b) 10. 說明:日程安排提前五分鐘提醒  11.
  • 鞏固SQL - 窗口函數&變量&數據透視圖
    但作為合格的一個數據分析師,sql的精通肯定是必不可少的,所以最近瘋狂刷sql題,同時也來總結下我以前比較少用的語法。*,rank() over( order by score desc) ranking ,dense_rank() over( order by score desc) dense_ranking,row_number() over( order by score desc) row_numfrom tb_score4.2、排名函數經典面試題
  • 程式設計師經典面試題,為什麼簡單的sql查詢,會這麼慢!
    大家都在說今年是程式設計師都不太好找工作,根據Boss直聘提供的數據,今年平均1份工作可以收到150個簡歷,競爭還是比較激烈的。今天給大家分享一個經典的程式設計師面試題,為什麼我只從Mysql中篩選幾行數據,執行速度卻非常慢呢。
  • 一道拼多多/阿里/字節都會考的sql面試題
    目前大數據發展勢頭強勁,各個公司大數據崗位需求不斷上漲,其中數據相關的崗位都逃不開hive/hadoop相關技術,面試中更是屢屢提及。今天我們來看一下一道在大廠頻繁出現的面試/筆試題目。要求使用hive-sql,不允許使用自定義的UDAF或者MR實現。題目分析:本題目的數據非常簡單,容易理解,難點在怎麼判斷「連續登錄」。我們知道sql的優點是處理行列式,通過簡單的代碼快速處理行列式的常規操作。
  • 解析 BAT 大廠的經典面試題(中篇)
    今天是周四(2020-05-xx),分享一句諺語 「讀書有三到,心到口到眼到」 。分享給大家的是 「工具 模塊」- 解析BAT面試題(中篇)。很多人對 BAT 以及其他大廠,也是朝思暮想。也因為一些原因,暫時還未能加入。