依托学生表(student)、选课表(sc)、课程表(course),对SQL常见的查询关键词:所有、平均、同一、同时、最多、最高等进行详解。

依托学生表(student)、选课表(sc)、课程表(course),对SQL常见的查询关键词:所有、平均、同一、同时、最多、最高等进行详解。

1. 查询语句基本结构:

select 列名1 | 表名1.列名 | 表名1.* | 聚合函数1 [,列名2 | 表名2.列名 | 表名2.* | 聚合函数2, ...]
from 表名1 | 子查询表1 [, 表名2 | 子查询表2, ...]
[where 条件1 [and | or 条件2, ...]
[group by 列名 
[having 聚合函数条件1 [and | or 聚合函数条件2, ...]]]
[order by 列名1 [desc] [, 列名2[desc], ...]]
[limit total | start, length]
]

2. 编写查询语句步骤:
2.1 定位表源,通过输出和条件判断,应从哪张表或哪些表中获取数据。
2.2 对于多张表,先将表进行连接。
2.3 包含聚合函数,考虑要不要分组,对于聚合函数条件的判断交由having子句处理(包含having,必定包含分组)。
3. 实例详述:

-- 1.查询每个学生成绩最高的成绩信息,输出学号、课程号、成绩。

select s.sno, c.cno, grade
from student s, sc, course c
where s.sno = sc.sno and sc.cno = c.cno and grade = (
-- 查询某个学生所有课程的最高分
select max(grade)
from sc
-- 将外部要查询的学号传入,与sc表连接
where s.sno = sno
-- 可分组,也可不分组,因为已经通过外部传入的学号将结果分组
group by sno
);

-- 2.查询同时选修了课程名为:高等数学,人工智能,数据结构的学生,输出学号,姓名。

select s.sno, sname
from student s, sc, course c
-- 筛选课程名为高等数学的学号
where s.sno = sc.sno and sc.cno = c.cno and cname = '高等数学' and s.sno in (
select s.sno
from student s, sc, course c
-- 再次筛选
where s.sno = sc.sno and sc.cno = c.cno and cname = '人工智能' and s.sno in (
select s.sno
from student s, sc, course c
-- 最终筛选
where s.sno = sc.sno and sc.cno = c.cno and cname = '数据结构'
)
);

-- 3.查询超过该课程平均分的成绩信息,输出学号、课程号、成绩。

select s.sno, c.cno, grade
from student s, sc, course c
where s.sno = sc.sno and sc.cno = c.cno and grade > (
-- 课程平均分
select avg(grade)
from sc
-- 将外部的课程号传入,与sc表连接
where c.cno = cno
);

-- 4.查询选课门数最多的学生的学号和姓名
select sno, sname
from student s
where sno in (
select sno
from sc
-- 传入外部学号,与sc表连接
where s.sno = sc.sno
having count(*) = (
-- 查询最多学了几门课
select max(sc_count.counter)
from (
select count(*) counter, cno
from student s, sc
where s.sno = sc.sno
-- 此处的学号在子查询内部,分组不可省略
group by s.sno
) sc_count
)
)

-- 5.查询与姓名为暖暖同一个系的学生信息。

select *
from student
where dno = (
-- 查询暖暖所在的系编号
select dno
from student
where sname = '暖暖'
)

-- 6.查询选修平均分为60分及以上的学生的各门课成绩,要求输出学号,姓名,课程名和成绩,并按学号升序排序。

select s.sno, sname, cname, grade
from student s, sc, course c
where s.sno = sc.sno and sc.cno = c.cno
-- 查询每个学生的平均分,需要对学号进行分组
group by sno
having avg(grade) >= 60;

-- 7.查询选修了全部课程的学生的学号,姓名,系编号。

select sno, sname, dno
from student s
-- 不存在这样的课程
where not exists (
select *
from course c
-- 不被学生选中
where not exists (
select *
from sc
-- 将三张表连接
where s.sno = sc.sno and sc.cno = c.cno
)
)

-- 8. 找出至今没有人选修过的课程,输出课程号、课程名。

select cno, cname
from course
-- 课程号不在
where cno not in (
select cno
from sc
group by cno
-- 至少有一个同学选了这门课程
having count(cno) > 0
)

-- 9.查询所有人都选修了的课程号与课程名。

select c.cno, cname
from student s, sc, course c
where s.sno = sc.sno and sc.cno = c.cno
group by c.cno
-- 选课人数
having count(*) = (
-- 学生总数
select count(*)
from student
)

4. 数据表


-- 删除

drop table sc;
drop table student;
drop table dept;
drop table course;

--系表

create table dept (
dNo int primary key auto_increment,
dName varchar(20) default '计算机系',
studentsCount int default 0
);

-- 学生表

create table student (
sNo int primary key auto_increment,
sex enum('男', '女') default '女',
sName varchar(20),
dNo int,
foreign key(dNo) references dept(dNo)
);

-- 课程表

create table course(
cNo int primary key auto_increment,
cName varchar(20),
credit float(2, 1),
classHour int
);
-- 成绩表
create table sc (
scNo int primary key auto_increment,
sNo int,
cNo int,
grade float(5, 2),
foreign key(sNo) references student(sNo),
foreign key(cNo) references course(cNo)
);

--初始化数据

insert into dept values
(1, '计算机系', 66), (2, '文学系', 55), (3, '外国语系', 88), (4, '金融系', 99);

insert into student values
(1, '女', '暖暖', 1),(2, '男', '山海', 1),(3, '女', '清欢', 1),(4, '女', '墨染', 1),
(5, '女', '大白', 2),(6, '男', '陌路', 2),(7, '女', '星辰', 2),(8, '女', '清律', 2),
(9, '女', '小白', 3),(10, '男', '奈何', 3),(11, '女', '大海', 3),(12, '女', '宇文', 3),
(13, '女', '轩怡', 4),(14, '男', '浅笑', 4),(15, '女', '玄泰', 4),(16, '女', '欧阳', 4);

insert into course values
(1, '高等数学', 5.0, 64),(2, '数据结构', 4.0, 56),(3, '人工智能', 3.0, 48),(4, 'Springboot', 2.0, 32);

insert into sc(sNo, cNo, grade) values
(1, 1, 88),(2, 1, 77),(3, 1, 66.0),(4, 1, 99),(5, 1, 78),(6, 1, 79),(7, 1, 97),(8, 1, 98),
(9, 1, 88),(10, 1, 77),(11, 1, 66.0),(12, 1, 99),
(1, 2, 88),(2, 2, 77),(3, 2, 66),(4, 2, 99),(5, 2, 78),(6, 2, 79),(7, 2, 97),(8, 2, 98),
(9, 2, 88),(10, 2, 77),(11, 2, 66),(12, 2, 99),(13, 2, 78),
(1, 3, 88),(2, 3, 77),(3, 3, 66),(4, 3, 99),(5, 3, 78),(6, 3, 79),(7, 3, 97),(8, 3, 98),
(9, 3, 88),(10, 3, 77),(11, 3, 66),(12, 3, 99),(13, 3, 78),(14, 3, 79),
(1, 4, 88),(2, 4, 77),(3, 4, 66),(4, 4, 99),(5, 4, 78),(6, 4, 79),(7, 4, 97),(8, 4, 98),
(9, 4, 88),(10, 4, 77),(11, 4, 66),(12, 4, 99),(13, 4, 78),(14, 4, 79),(15, 4, 97),(16, 4, 98);

熬夜伤身,祝你一夜好眠。

  • 2
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
交互式SQL的使用 环境:WINDOWS,Microsoft SQL Server 实验要求: 1,创建Student数据库,包括Students,Courses,SC结构如下: Students(SNO,SNAME,SEX,BDATE,HEIGHT,DEPARTMENT) Courses(CNO,CNAME,LHOUR,CREDIT,SEMESTER) SC(SNO,CNO,GRADE) (注:下划线示主键,斜体示外键),并插入一定数据。 2.完成如下的查询要求及更新的要求。 (1)查询身高大于1.80m的男生的学号和姓名; (2)查询计算机系秋季所开课程课程号和学分数; (3)查询选修计算机系秋季所开课程的男生的姓名、课程号、学分数、成绩; (4)查询至少选修一门电机系课程的女生的姓名(假设电机系课程课程号以EE开头); (5)查询每位学生已选修课程的门数和总平均成绩; (6)查询每门课程选课学生人数,最高成绩,最低成绩和平均成绩; (7)查询所有课程的成绩都在80分以上的学生的姓名、学号、且按学号升序排列; (8)查询缺成绩的学生的姓名,缺成绩的课程号及其学分数; (9)查询有一门以上(含一门)三个学分以上课程的成绩低于70分的学生的姓名; (10)查询1984年~1986年出生的学生的姓名,总平均成绩及已修学分数。 (11) 在STUDENTSC关系中,删去SNO以’01’开关的所有记录。 (12)在STUDENT关系中增加以下记录: (13)将课程CS-221的学分数增为3,讲课时数增为60 3.补充题: (1) 统计各系的男生和女生的人数。 (2) 列出学习过‘编译原理’,‘数据库’或‘体系结构’课程,且这些课程的成绩之一在90分以上的学生的名字。 (3) 列出未修选‘电子技术’课程,但选修了‘数字电路’或‘数字逻辑’课程学生数。 (4) 按课程排序列出所有学生的成绩,尚无学生选修的课程,也需要列出,相关的学生成绩用NULL示。 (5) 列出平均成绩最高学生名字和成绩。(SELECT句中不得使用TOP n子句) 4.选做题:对每门课增加“先修课程”的属性,用来示某一门课程的先修课程,每门课程应可记录多于一门的先修课程。要求: 1) 修改结构的定义,应尽量避免数据冗余,建立必要的主键,外键。 2) 设计并插入必要的测试数据,完成以下查询: 列出有资格选修数据库课程的所有学生。(该学生已经选修过数据库课程的所有先修课,并达到合格成绩。) 注意:须设计每个查询的测试数据,并在查询之前用INSERT语句插入表中。 提交作业形式: 1) 建立Student数据库SQL脚本,插入所有数据项的SQL脚本(包括所有的测试数据)。 2) 完成查询要求的SQL语句脚本。 3) 选做题:须提交修改数据库定义的SQL脚本,插入测试数据的SQL脚本以及用于查询SQL语句。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Qian_Qian_IT

感谢您的赏识,我将持续创作~

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值