SqlServer 常见SQL笔试题之语句操作题详解1

本文涉及的产品
RDS SQL Server Serverless,2-4RCU 50GB 3个月
推荐场景:
云数据库 RDS SQL Server,基础系列 2核4GB
简介: SqlServer 常见SQL笔试题之语句操作题详解1

SqlServer常见SQL笔试题之语句操作题详解


测试数据库

CREATEDATABASE handWriting

ONPRIMARY

(

   name='bishi',

   fileName='E:\数据库\bishi.mbf',

   size= 5MB,

   maxSize= 30MB,

   fileGrowth= 10%

)

LOGON

(

   name='bishilog',

   fileName='E:\数据库\bishilog.ldf',

   size= 5MB,

   fileGrowth= 10%

)

 

1、  

有个表:

employee职工(工号,姓名,性别,年龄,部门)(numnamesexagedepartmentno)

wage工资(编号,工资金额)(IDamount)

attend出勤(工号,工资编号,出勤率)(numIDattendance)

请根据要求,编写相应的SQL语句。

 

--写一个SQL语句,查询工资金额为8000的职工工号和姓名。

分析:多表查询(3表或以上),先对第一个和第二个表按照两表连接做查询,然后用查询结果和第三个表做连接查询,以此类推,直到所有的表都连接上为止,最终形成一个中间的结果表,然后根据WHERE条件过滤中间表的记录,并根据SELECT指定的列返回查询结果。

SELECTname,employee.num FROM  employee, wage, attend

WHEREemployee.num = attend.num and attend.ID = wage.ID and wage.amount = 8000

 

--写一个SQL语句,查询职工张三的出勤率

分析:只涉及到两张表。。如下

SELECT attendance FROM  attend, employee

WHEREattend.num = employee.num AND employee.name ='张三'

--WHERE num = (SELECT  num FROM  employee WHERE employee.name = '张三')

 

--写一个SQL语句,查询3次出勤率为0的职工姓名和工号【常见题目】

分析:设计到两张表,相关子查询,employee表中每给出一个工号,就去全表扫描attend表,先在表attend中查找满足WHERE条件的记录,然后对结果进行分组,再过滤出勤率为0的,对每一个num,虚表都有值,那么exists虚表返回true,把结果放入结果集表中,然后再指向下一个记录,给定一个num重复。。。。

SELECTname, num FROM  employee

WHEREEXISTS(

SELECT num FROM  attend

WHEREemployee.num = attend.num and attendance = 0

GROUPBY num HAVINGCOUNT(*)= 3)

 

--写一个SQL语句,查询出勤率为10并且工资金额小于2500的职工信息。[常见题目]

分析:不可行的思路:职工信息在表employee,工资在表wage,出勤率在表attend中,工资表只和出勤表相关联,先从表attend和表wage选出满足条件的结果集,再通过num和表employee相关联

SELECT*FROM  employee,(

SELECT*FROM  attend, wage

WHEREattendance = 10 AND attend.ID = wage.ID and amount <</span> 2500) A

WHEREemployee.num = A.num

说明:多次为'A'指定了列'ID'  这种方法不可行,字段太多,会同名,要全部写出来。。

 

思路二:多表连接,【一般这种做法错不了,具有普遍性】,num的选择,来自attendnum集合,ID来自满足条件的集合

SELECT*FROM  employee

WHEREnum IN(

SELECT num FROM  attend

WHEREattendance = 10 and ID IN(

SELECT ID FROM  wage

WHEREamount <</span> 2500))

 

2、  

为管理岗位业务培训信息,建立个表:

  S (S#,SN,SD,SA) S#,SN,SD,SA分别代表学号、学员姓名、所属单位、学员年龄

  C (C#,CN ) C#,CN分别代表课程编号、课程名称

  SC ( S#,C#,G ) S#,C#,G分别代表学号、所选修的课程编号、学习成绩

--使用标准SQL嵌套语句查询选修全部课程的学员姓名和所属单位【常见题目】

错误做法如下,

SELECT sn, sd FROM  s

WHEREEXISTS(

SELECT*FROM  c

WHEREEXISTS(

SELECT*FROM  sc

WHERE  s.s# = sc.s# and c.c# = sc.c#))

说明:先装载s表,然后,指针p1指向第一个记录了,然后装载c表,指针p2指向第一个记录,

然后装载sc表,进行全sc表扫描,指针指向第一个记录,然后查询满足WHERE的记录,如果找到记录(不管一条还是多条),则内层中的EXISTS虚表返回值为真,执行SELECT  * FROM  C把结果放入虚表中,显然虚表中有数据,外层EXISTS虚表为真,然后把snsd放入最终结果表,这不说明他选了全部课程,只能说明他至少选了一门课程

 

正确做法:语义上:查询这样的学生,他没有选的课程不存在。--双重否定

对每个学生,去课程表中查找没被他选修的课程,结果找不到数据。

SELECT sn, sd

FROM s

WHERE NOT EXISTS

(

   SELECT * FROM c

   WHERE NOT EXISTS

   (

       SELECT * FROM sc

       WHERE s.s# = sc.s# and sc.c# = c.c#

   )

)

 

--以下子查询即为查找他没选修的课程

   SELECT * FROM c

   WHERE NOT EXISTS

   (

       SELECT * FROM sc

       WHERE s.s# = sc.s# and sc.c# = c.c#

   )

 

--查询选修了课程的学员人数【常见题目】

分析:选修课中去掉重复的学员号s#,剩下的记录个数就表示人数

SELECT 学员人数=COUNT(DISTINCT s#)FROM  SC

 

--查询选修课程超过5门的学员学号和所属单位【常见题目】

分析:同一个学生(分组使相同值的学号放在一组),选修课程超过5门(该组的记录个数超过5个)

(HAVING提出要求,记录个数用count实现)

先从sc表中查找,然后分组,选择记录大于5的,然后再从s表查找,条件是学生号在刚才那个sc表查询结果集中。

SELECT sn, sd FROM  S

WHEREs# IN(

SELECT s# FROM  SC

GROUPBY s#

HAVINGCOUNT(DISTINCT C#)>5)

 

注意:如果仅是group by,不带having语句,那么针对每个分组仅会产生一条记录,如果使用having语句则会产生1n条记录,每条记录都必须满足having给定的条件。

 

--使用标准SQL嵌套语句查询选修课程名称为税收基础的学员学号和姓名

分析:三表csc,s

SELECT s#,sn FROM  s

WHEREs# IN(

SELECT s# FROM  sc WHERE c# IN(

SELECT c# FROM  c

WHEREcn ='税收基础'))

 

--使用标准SQL嵌套语句查询选修课程编号为2的学员姓名和所属单位

SELECT s#,sd FROM  s

WHEREs# IN(

SELECT s# FROM  sc WHERE c# IN(

SELECT c# FROM  c

WHEREc# ='2'))

 

--使用标准SQL嵌套语句查询不选修课程编号为’5’的学员姓名和所属单位

SELECT s#,sd FROM  s

WHEREs# IN(

SELECT s# FROM  sc WHERE c# IN(

SELECT c# FROM  c

WHEREc# <>'5'))

 

--用一条SQL语句查询出每门课都大于80分的学生姓名【常见题目】

分析:涉及选修表,学生表,对sc表里的每个s#,全表扫描他选修的成绩,都要大于80

语义:查找这样的学生,全表扫描他选修的成绩,不存在小于80

SELECT sn FROM  s

WHEREs# IN(

SELECT x.s# FROM  sc x

WHERENOTEXISTS(

SELECT*FROM  sc y

WHEREy.s# = x.s# AND g <</span> 80))

 

3、  

问题描述:

已知关系模式:

S1 (SNO,SNAME)学生关系。SNO为学号,SNAME为姓名

C1 (CNO,CNAME,CTEACHER)课程关系。CNO为课程号,CNAME为课程名,CTEACHER为任课教师

SC1(SNO,CNO,SCGRADE)选课关系。SCGRADE为成绩

 

--3.1.找出没有选修过李明老师讲授课程的所有学生姓名【常见题型】

法一:等值连接查询

SELECT SNAME FROM  S1,C1, SC1

WHERE S1.SNO = SC1.SNO

  AND S1.SNO = C1.CNO

  AND C1.CTEACHER <>'李明'

 

法二:和方法一一样的原理

SELECT SNAME FROM  S1

WHERE SNO IN(

 SELECT  SNO FROM  SC1

  WHERE CNO IN(

   SELECT  CNO FROM  C1

    WHERE CTEACHER <>'李明'))

 

法三

[错误做法]

SELECT SNAME FROM  S1

WHERENOTEXISTS(

 SELECT  *FROM  C1

  WHERENOTEXISTS(

   SELECT  *FROM  SC1

    WHERE CTEACHER ='李明'AND S1.SNO = SC1.SNO AND C1.CNO = SC1.CNO ))

 

[正解如下]

语义:查询这样的学生,不存在被李明老师讲且被他选修的课程。

SELECT SNAME FROM  S1

WHERE NOTEXISTS(

 SELECT  *FROM  C1

  WHEREEXISTS(

   SELECT  *FROM  SC1

    WHERE CTEACHER ='李明'AND S1.SNO = SC1.SNO AND C1.CNO = SC1.CNO ))

 

--查找被李明老师讲且被选修课程

 SELECT  *FROM  C1

  WHEREEXISTS(

   SELECT  *FROM  SC1

    WHERE CTEACHER ='李明'AND S1.SNO = SC1.SNO AND C1.CNO = SC1.CNO ))

 

--3.2.列出有二门以上(含两门)不及格课程的学生姓名及其平均成绩【常见题型】

分析:

语义:查询这样的学生的姓名及学生的平均成绩,选修课程至少有两名门不及格

培养解题习惯-->涉及表:姓名--S1表,成绩--SC1表,关联字段SNO,条件--同一个学生,两门或两门以上不及格,用到函数--VAG()

条件WHERE,至少要有两门用COUNT,同一个同学,分组GROUP BY

 

假如这里没有要求查询平均成绩,那么可以如下

SELECT S1.SNAME FROM  S1

WHEREEXISTS(

SELECT*FROM  SC1 WHERE SC1.SNO = S1.SNO AND SC1.SCGRADE <</span> 60

GROUPBY SC1.SNO HAVINGCOUNT(*)>= 2);

 

但是这里还要求平均成绩,我们可以这样,在上一步的基础上,把EXISTS子句中的语句提取出来的结果表给取个别名,然后,两表查询

SELECT S1.SNAME, A.AVGSCORE FROM  S1,

(SELECT SNO,AVG(SCGRADE) AVGSCORE FROM  SC1

WHERESCGRADE <</span> 60

GROUPBY SC1.SNO HAVINGCOUNT(*)>= 2) A

WHERES1.SNO = A.SNO

 

--3.3.列出既学过“1”号课程,又学过“2”号课程的所有学生姓名【常见题型】

做法1

SELECT SNAME

 FROM  S1,(

SELECT SNO FROM  SC1

WHERECNO = 1

INTERSECT

SELECT SNO FROM  SC1

WHERECNO = 2

)A

WHERES1.SNO = A.SNO

相关实践学习
使用SQL语句管理索引
本次实验主要介绍如何在RDS-SQLServer数据库中,使用SQL语句管理索引。
SQL Server on Linux入门教程
SQL Server数据库一直只提供Windows下的版本。2016年微软宣布推出可运行在Linux系统下的SQL Server数据库,该版本目前还是早期预览版本。本课程主要介绍SQLServer On Linux的基本知识。 相关的阿里云产品:云数据库RDS&nbsp;SQL Server版 RDS SQL Server不仅拥有高可用架构和任意时间点的数据恢复功能,强力支撑各种企业应用,同时也包含了微软的License费用,减少额外支出。 了解产品详情:&nbsp;https://www.aliyun.com/product/rds/sqlserver
目录
相关文章
|
2月前
|
SQL 数据库
执行 Transact-SQL 语句或批处理时发生了异常。 (Microsoft.SqlServer.ConnectionInfo)之解决方案
执行 Transact-SQL 语句或批处理时发生了异常。 (Microsoft.SqlServer.ConnectionInfo)之解决方案
263 0
|
4月前
|
SQL XML 运维
SQL Server 运维常用sql语句(三)
SQL Server 运维常用sql语句(三)
28 1
|
4月前
|
Java 应用服务中间件 Maven
从零到英雄:一步步构建你的首个 JSF 应用程序,揭开 JavaServer Faces 的神秘面纱
【8月更文挑战第31天】JavaServer Faces (JSF) 是一种强大的 Java EE 标准,用于构建企业级 Web 应用。它提供了丰富的组件库和声明式页面描述语言 Facelets,便于开发者快速开发功能完善且易于维护的 Web 应用。本文将指导你从零开始构建一个简单的 JSF 应用,包括环境搭建、依赖配置、Managed Bean 编写及 Facelets 页面设计。
100 0
|
4月前
|
SQL 关系型数据库 MySQL
【超全整理】SQL日期与时间函数大汇总会:MySQL与SQL Server双轨对比教学,助你轻松搞定时间数据处理难题!
【8月更文挑战第31天】本文介绍了在不同SQL数据库系统(如MySQL、SQL Server、Oracle)中常用的日期与时间函数,包括DATE、NOW()、EXTRACT()、DATE_ADD()、TIMESTAMPDIFF()及日期格式化等,并提供了具体示例。通过对比这些函数在各系统中的使用方法,帮助开发者更高效地处理日期时间数据,满足多种应用场景需求。
426 0
|
4月前
|
SQL 关系型数据库 MySQL
SQL Server、MySQL、PostgreSQL:主流数据库SQL语法异同比较——深入探讨数据类型、分页查询、表创建与数据插入、函数和索引等关键语法差异,为跨数据库开发提供实用指导
【8月更文挑战第31天】SQL Server、MySQL和PostgreSQL是当今最流行的关系型数据库管理系统,均使用SQL作为查询语言,但在语法和功能实现上存在差异。本文将比较它们在数据类型、分页查询、创建和插入数据以及函数和索引等方面的异同,帮助开发者更好地理解和使用这些数据库。尽管它们共用SQL语言,但每个系统都有独特的语法规则,了解这些差异有助于提升开发效率和项目成功率。
408 0
|
3月前
|
关系型数据库 MySQL 网络安全
5-10Can't connect to MySQL server on 'sh-cynosl-grp-fcs50xoa.sql.tencentcdb.com' (110)")
5-10Can't connect to MySQL server on 'sh-cynosl-grp-fcs50xoa.sql.tencentcdb.com' (110)")
|
5月前
|
SQL 存储 监控
SQL Server的并行实施如何优化?
【7月更文挑战第23天】SQL Server的并行实施如何优化?
115 13
|
5月前
|
SQL
解锁 SQL Server 2022的时间序列数据功能
【7月更文挑战第14天】要解锁SQL Server 2022的时间序列数据功能,可使用`generate_series`函数生成整数序列,例如:`SELECT value FROM generate_series(1, 10)。此外,`date_bucket`函数能按指定间隔(如周)对日期时间值分组,这些工具结合窗口函数和其他时间日期函数,能高效处理和分析时间序列数据。更多信息请参考官方文档和技术资料。
|
5月前
|
SQL 存储 网络安全
关系数据库SQLserver 安装 SQL Server
【7月更文挑战第26天】
63 6