首先是建立練習使用各種表格(這里使用的是SQL server建立的):
use school; -- 創建學生表 create table Student( Sno varchar(20), Sname varchar(20) not null, Ssex varchar(20) not null, Sbirthday datetime, Class varchar(20) ); -- 創建教師表 create table Teacher( Tno varchar(20), Tname varchar(20) not null, Tsex varchar(20) not null, Tbrithday datetime, Prof varchar(20), Depart varchar(20) not null ); -- 創建課程表 create table Course( Cno varchar(20), Cname varchar(20) not null, Tno varchar(20) not null, ); -- 創建成績表 create table Score( Sno varchar(20) not null, Cno varchar(20) not null, -- 成績 Degree Decimal ); --添加約束 --為學生表添加約束,把列Sno作為主鍵約束,把列Ssex添加檢查約束 alter table Student add constraint CK_Sno check(Sno is not null), --為列Sno添加非空約束 constraint PK_Sno primary key(Sno), --為列Sno添加主鍵約束 constraint CK_Ssex check(Ssex='男' or Ssex='女') --為列Ssex添加檢查約束,令列Ssex列只能輸入男或女 --為課程表添加約束 alter table Course add constraint CK_Cno check(Cno is not null), constraint PK_Cno primary key(Cno), --為列Cno添加主鍵約束 constraint UQ_Cname unique(Cname) --為列Cname添加唯一約束 --為教師表格添加約束,為列Tno添加主鍵約束,為列Tsex添加檢查約束,為列Depart添加外鍵約束 alter table Teacher add constraint CK_Tno check(Tno is not null), constraint PK_Tno primary key(Tno), --為列Tno添加主鍵約束 constraint CK_Tsex check(Tsex='男' or Tsex='女') --為列Tsex添加檢查約束 go --添加數據 -- 添加學生信息 insert into student values('108','曾華','男','1977-09-01','95033'); insert into student values('105','匡明','男','1975-10-02','95031'); insert into student values('107','王麗','女','1976-01-23','95033'); insert into student values('101','李軍','男','1976-02-20','95033'); insert into student values('109','王芳','女','1975-02-10','95031'); insert into student values('103','陸君','男','1974-06-03','95031'); -- 添加教師信息 insert into teacher values('804','李誠','男','1958-12-02','副教授','計算機系'); insert into teacher values('856','張旭','男','1969-03-12','講師','電子工程系'); insert into teacher values('825','王萍','女','1972-05-05','助教','計算機系'); insert into teacher values('831','劉冰','女','1977-08-14','助教','電子工程系'); -- 添加課程信息 insert into course values('3-105','計算機導論','825'); insert into course values('3-245','操作系統','804'); insert into course values('6-166','數字電路','856'); insert into course values('9-888','高等數學','831'); -- 添加成績信息 insert into score values('103','3-245','86'); insert into score values('105','3-245','75'); insert into score values('109','3-245','68'); insert into score values('103','3-105','92'); insert into score values('105','3-105','88'); insert into score values('109','3-105','76'); -- insert into score values('103','3-105','64'); -- insert into score values('105','3-105','91'); -- insert into score values('109','3-105','78'); -- 這三行數據在樣例里面給出,但是主鍵重復了。- -,報錯嚇了我一跳 insert into score values('103','6-166','85'); insert into score values('105','6-166','79'); insert into score values('109','6-166','81') go
接下來是練習題及答案:
--1、 查詢Student表中的所有記錄的Sname、Ssex和Class列。 select Sname, Ssex, Class from Student --2、 查詢教師所有的單位即不重復的Depart列。 select distinct Depart,Tname from Teacher --3、查詢Student表的所有記錄。 select * from Student --4、查詢Score表中成績在60到80之間的所有記錄 select * from Score where Degree between 60 and 80 --5、查詢Score表中成績為85,86或88的記錄。 select * from Score where Degree in (85,86,88) --6、查詢Student表中“95031”班或性別為“女”的同學記錄。 select * from Student where Ssex='女' or Class='95031' --7、以Class降序查詢Student表的所有記錄。 select * from Student order by Class desc --8、以Cno升序、Degree降序查詢Score表的所有記錄。 select * from Score order by Cno,Degree desc --多個條件用","來分隔 --9、查詢“95031”班的學生人數。 select count(*) from Student where Class='95031' --10、 查詢Score表中的最高分的學生學號和課程號。(子查詢或者排序) select Sno,Cno from Score where Degree = (select max(degree) from score) select top 1 Sno,Cno from Score order by Degree desc --11、查詢每門課的平均成績,要按照課程分組group by,然后求沒門課平均avg select Cno, convert(numeric(18,2),avg(Degree)) 平均成績 from Score group by Cno --12、查詢Score表中至少有5名學生選修的並以3開頭的課程的平均分數。 select Cno,avg(Degree) from Score group by Cno having Cno like '3%' and Cno in (select Cno from Score group by Cno having count(Cno) > 2) --Like模糊查詢 3%以3開頭 having只能跟在group by 后面 --13、查詢分數大於70,小於90的Sno列。 select Sno from Score where Degree between 70 and 90 --14、查詢所有學生的Sname、Cno和Degree列。 select A.Sno,A.Degree,B.Sname from Score as A inner join Student as B on A.Sno = B.Sno --15、查詢所有學生的Sno、Cname和Degree列。 select A.Sno,A.Degree,C.Cname from Score as A inner join Course as C on A.Cno = C.Cno go --16、查詢所有學生的Sname、Cname和Degree列。 select S.Sname,A.Degree,C.Cname from Score as A inner join Course as C on A.Cno = C.Cno inner join Student as S on S.Sno=A.Sno go --17、 查詢“95033”班學生的平均分。 select S.Class as 班級 ,avg(A.Degree) as 評分分 from Score as A inner join Student as S on S.Sno = A.Sno group by S.Class --建立新表grade表 create table grade (low int,upp int,ranks char(1)) insert into grade values(90,100,'A') insert into grade values(80,89,'B') insert into grade values(70,79,'C') insert into grade values(60,69,'D') insert into grade values(0,59,'E') select * from grade --現查詢所有同學的Sno、Cno和rank列。 --方法一 select * , (select ranks from grade where low < Degree and Upp >= Degree) as 評級 from Score 方法二 select A.* , G.ranks from Score as A inner join grade as G on A.Degree between G.low and G.upp --19、 查詢選修“3-105”課程的成績高於“109”號同學成績的所有同學的記錄。 select * from Score where Degree > (select Degree from Score where Sno='109' and Cno = '3-105') and Cno = '3-105' --20、查詢score中選學多門課程的同學中分數為非最高分成績的記錄。 Select * from score a where degree <(select max(degree) from Score b where b.Cno=a.Cno) and Sno in (select Sno from Score group by Sno having count(*)>1) --結合條件一定要寫在子查詢中,子查詢內部設定的關聯名稱,只能在該子查詢內部使用,也就是說內部可以看到外部,而 --外部看不到內部 --SQL是按照先內層子查詢后補外層查詢的順序來執行的,這樣,子查詢執行結束后只會留下執行結果. --22、查詢和學號為105的同學同年出生的所有學生的Sno、Sname和Sbirthday列。 select * from Score AS A inner join Student AS S on A.Sno=S.Sno where year(S.Sbirthday) = (select year(Sbirthday) from Student where Sno='105') --23、查詢“張旭“教師任的學生成績。 select A.* from Teacher as T inner join Course as C on T.Tno=C.Tno inner join Score AS A on A.Cno=C.Cno where T.Tname='張旭' --24、查詢選修某課程的同學人數多於5人的教師姓名。 select A.Cno,T.Tname,Count(A.Cno) from Teacher as T inner join Course as C on T.Tno=C.Tno inner join Score AS A on A.Cno=C.Cno group by A.Cno,T.Tname --25、查詢95033班和95031班全體學生的記錄。 select * from Student where Class='95033' or Class='95031' --26、 查詢存在有85分以上成績的課程Cno. select Cno from Score where Degree > 85 group by Cno --27、查詢出“計算機系“教師所教課程的成績表。 select A.* from Teacher as T inner join Course as C on T.Tno=C.Tno inner join Score AS A on A.Cno=C.Cno where T.Depart='計算機系' --28、查詢“計算機系”與“電子工程系“不同職稱的教師的Tname和Prof。? select Prof,Depart from Teacher as a where Prof not in (select Prof from Teacher as b where b.Depart <> a.Depart) --29、查詢選修編號為“3-105“課程且成績至少高於選修編號為“3-245”的同學的記錄 select * from Score as A inner join Student as S on A.Sno = S.Sno where Cno = '3-105' and Degree > (select Degree from Score as B where B.Sno=A.Sno and B.Cno='3-245') --31、 查詢所有教師和同學的name、sex和birthday. select Sname, Ssex, convert(date,Sbirthday) from Student union (select Tname,Tsex,convert(date,Tbrithday) from Teacher) --32、查詢所有“女”教師和“女”同學的name、sex和birthday. select Sname as name, Ssex as sex, convert(date,Sbirthday) as birthday from Student where Ssex='女' union (select Tname,Tsex,convert(date,Tbrithday) from Teacher where Tsex='女') --33、 查詢成績比該課程平均成績低的同學的成績表。 select * from Score as a where Degree < (select avg(Degree) from Score as b where b.Cno=a.Cno group by b.Cno) --34、查詢所有任課教師的Tname和Depart. select Tname,Depart from Teacher --35 、查詢所有未講課的教師的Tname和Depart. select * from Teacher where Tno not in (select Tno from Course where Cno in (select Cno from Score)) --36、查詢至少有2名男生的班號。 select Class from Student where Ssex='男' group by Class having Count(Class)>=2 --37.查詢不姓王的同學信息 select * from Student where Sname not like '王%' --38、查詢Student表中每個學生的姓名和年齡。 select Sname,Ssex from Student --39、查詢Student表中最大和最小的Sbirthday日期值。 select max(Sbirthday) as 最大日期值,min(Sbirthday) as 最小日期值 from Student --40、以班號和年齡從大到小的順序查詢Student表中的全部記錄。 select * from Student order by Class,Sbirthday desc --41、查詢“男”教師及其所上的課程。 select T.Tname, C.Cno from Teacher as T inner join Course as C on T.Tno=C.Tno where T.Tsex='男' --42、查詢最高分同學的Sno、Cno和Degree列。 select * from Score where Degree =(select max(Degree) from Score ) --43、查詢和“李軍”同性別的所有同學的Sname. select Sname from Student where Ssex=(select Ssex from Student where Sname='李軍') and Sname <> '李軍' --44、查詢和“李軍”同性別並同班的同學Sname. select Sname from Student where Ssex=(select Ssex from Student where Sname='李軍') and Sname <> '李軍' and Class = (select Class from Student where Sname='李軍') --45、查詢所有選修“計算機導論”課程的“男”同學的成績表。SQL語句 select * from Score where Sno in (select Sno from Student where Ssex='男') and Cno in (select Cno from Course where Cname='計算機導論')
--46,查詢" 3-245 "課程比" 3-105 "課程成績高的學生的信息及課程分數 select * from Score as A inner join Score as B on A.Sno = B.Sno where A.Cno='3-245' and B.Cno='3-105' and A.Degree < B.Degree --47.查詢各科成績的最高分及最低分及格率,中等率,優良率,優秀率 --及格為>=60,中等為:70-80,優良為:80-90,優秀為:>=90 --要求輸出課程號和選修人數,查詢結果按人數降序排列,若人數相同,按課程號升序排列 select Cno as 科目, Max(Degree) as 最高分, MIn(Degree) as 最低分, convert(int,avg(Degree)) as 平均分 , convert(varchar(20),convert(numeric(10,2),convert(numeric(10,2),sum(case when Degree >= 60 then 1 else 0 end))/Count(Cno)*100)) + '%' as 及格率, convert(varchar(20),convert(numeric(10,2),convert(numeric(10,2),sum(case when Degree >= 70 and Degree <80 then 1 else 0 end))/Count(Cno)*100)) + '%' as 中等率, convert(varchar(20),convert(numeric(10,2),convert(numeric(10,2),sum(case when Degree >=80 and Degree < 90 then 1 else 0 end))/Count(Cno)*100)) + '%' as 優良率, convert(varchar(20),convert(numeric(10,2),convert(numeric(10,2),sum(case when Degree >= 60 then 1 else 0 end))/Count(Cno)*100) )+ '%' as 優秀率 from Score group by Cno order by count(Cno),Cno --48.按各科成績進行排序,並顯示排名, degree 重復時保留名次空缺 select * , rank() over(partition by Cno order by Degree) as 排名 from Score --49查詢各科成績前兩名的記錄 select * from(select * , rank() over(partition by Cno order by Degree) as 排名 from Score) as A where A.排名 <=2 --50查詢所有學生的課程及分數情況(存在學生沒成績,沒選課的情況) select S.Sno,A.* from Student as S left join Score as A on S.Sno=A.Sno --51.查詢不同課程成績相同的學生的學生編號、課程編號、學生成績 select * from Score as A inner join Score as B on A.Sno = B.Sno where A.Cno <> B.Cno and A.Degree = B.Degree