> 文档中心 > 【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

文章目录

    • 前言
    • 1.数据查询
      • 1.1单表查询
        • 1.1.1选择表中的若干列
          • 1.1.1.1查询指定列
          • 1.1.1.2查询全部列
          • 1.1.1.3查询经过计算的值
          • 1.1.1.4使用列别名改变查询结果的列标题
          • 1.1.1.5对查询结果大小写转换
        • 1.1.2选择表中的若干元组
          • 1.1.2.1消除取值重复的行
          • 1.1.2.2询满足条件的元组
            • 1.1.2.2.1比较大小
            • 1.1.2.2.2确定范围
            • 1.1.2.2.3确定集合
            • 1.1.2.2.4字符串匹配
            • 1.1.2.2.5涉及空值的查询
            • 1.1.2.2.6多重条件查询
            • 1.1.2.2.7对查询结果排序
            • 1.1.2.2.8使用集函数
            • 1.1.2.2.9对查询结果分组

前言

        上篇博主带大家学习了数据库的数据定义(DDL),如果没学且感兴趣的的小伙伴可以点击前去了解一下:
【Mysql 一周速成Mysql】 第二篇SQL语法 – 数据定义(SQL DDL)进阶提升。
       今天博主给大家带来SQL语法之查询(Select)–单表查询。

1.数据查询

       数据查询是把数据在数据库的表中提取出来,供人查看和使用。

1.1单表查询

        单表查询,顾名思义就是对一个表进行查询。
查询仅涉及一个表,是一种最简单的查询操作;查询操作包括选择表中的若干列,选择表中的若干元组, 对查询结果排序,使用集函数,对查询结果分组 等。它的语句格式为:

Select [All|Distinct]  [,] …From  [, ] …[ Where  ][ Group By  [ Having  ] ][ Order By [ ASC|DESC ] ];

       下面通过例子来感受下单表查询的魅力吧。

1.1.1选择表中的若干列

       假设有一学生表Student,包括Sno(学号),Sname(姓名),Ssex(性别),Sage(年龄),Sdept(院系)这些列。
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

1.1.1.1查询指定列

[例1] 查询全体学生(Student)的学号(Sno)与姓名(Sname)

Select Sno,SnameFrom  Student; 

[例2] 查询全体学生的姓名、学号、所在系(Sdept)

Select Sname,Sno,SdeptFrom  Student;
1.1.1.2查询全部列

[例3] 查询全体学生的详细记录。

Select  Sno,Sname,Ssex,Sage,SdeptFrom  Student; 

Select  *From  Student; 
1.1.1.3查询经过计算的值

       Select子句的为表达式,包括算术表达式、字符串常量、函数、列别名等。
[例4] 查全体学生的姓名及其出生年份。

Select Sname,2022-SageFrom  Student; 

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

1.1.1.4使用列别名改变查询结果的列标题

       当然,可以用as给列名临时重命名(列别名),根据上个例子,我们把可以2021-Sage临时命名为 Birth这样写:

Select Sname,2021-Sage as BirthFrom  Student; 

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升
再如:

Select Sname 姓名,‘Year of Birth:’ ,2021-Sage  出生年份,  (Sdept)  院系From  Student;

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

1.1.1.5对查询结果大小写转换

       还可以对查询出来的结果进行大小写转换大写:Upper(列名)、小写:Lower(列名):
[例5] 查询全体学生的姓名、出生年份和所有系,要求用小写字母表示所有系名。

Select Sname,'Year of Birth:',2021-Sage, Lower(Sdept)From  Student; 

大写字母:Upper()
结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升当然,表中数据是大写。

1.1.2选择表中的若干元组

       假设SC表存在以下列和数据:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

       Course表存在以下列和数据:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升
       Student表存在以下列和数据:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

1.1.2.1消除取值重复的行

在进行查询的时候Mysql默认是输出所有行的。
[例6] 查询选修了课程的学生学号

Select Sno  From SC;或(默认 All)Select All Sno From  SC;

查询结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

       显然,我们针对上述问题的想要的结果并不是上面的输出结果,这样的结果数据冗余,我们只是想看见一个就好,那么我们就要对数据进行消除冗余,引入Distinct,这样我们的道德结果就是预期结果。

Select Distinct SnoFrom  SC;

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升
    需要注意的是: Distinct短语的作用范围是所有目标列。

Select Distinct Cno,Distinct SnoFrom  SC; --这样写是错误的!

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升
下列写法就是正确的:

Select Distinct Cno,SnoFrom  SC; 

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

1.1.2.2询满足条件的元组

    Where子句常用的查询条件,包括以下:

【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

1.1.2.2.1比较大小

    在Where子句的中使用比较运算符
=,>,=,<=,!= 或 ,!>,!<, 逻辑运算符Not + 比较运算符。
[例7] 查询所有年龄在20岁以下的学生姓名及其年龄

Select Sname,Sage From    Student    Where Sage = 20; 

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

1.1.2.2.2确定范围

    使用谓词 Between … And …、Not Between … And …、test_expression 必须与 begin_expression 和 end_expression 具有相同的数据类型 。
[例9] 查询年龄在20~23岁(包括20岁和23岁)之间的学生的姓名、系别和年龄

Select Sname,Sdept,SageFrom    StudentWhere Sage Between 20 And 23;

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升
[例10] 查询年龄不在20~23岁之间的学生姓名、系别和年龄

Select Sname,Sdept,SageFrom    StudentWhere Sage NOT BETWEEN 20 AND 23;

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

1.1.2.2.3确定集合

我们用IN表示在集合中where 列 IN、NOT IN(数据1,数据2);
[例10] 查询年为20或21岁的学生姓名、系别和年龄

Select Sname,Sdept,SageFrom    StudentWhere Sage = 20 or Sage = 21;或者Select Sname,Sdept,SageFrom    StudentWhere Sage in (20 , 21);

【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升
[例11] 查询年不为20或21岁的学生姓名、系别和年龄

Select Sname,Sdept,SageFrom    StudentWhere Sage != 20 or Sage != 21;或者Select Sname,Sdept,SageFrom    StudentWhere Sage NOT IN(20 , 21);

输出结果:
【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升

1.1.2.2.4字符串匹配

    [Not] Like ‘’ [Escape ‘ ’],指定匹配模板,固定字符串或含通配符的字符串;当匹配模板为固定字符串时,可以用 = 运算符取代, Like 谓词用 != 或 运算符取代 Not Like 谓词。
通配符:
% (百分号) 代表任意长度(长度可以为0)的字符串
例:a%b 刘%
_ (下横线) 代表任意单个字符
例:a_b

1)匹配模板为固定字符串
[例12] 查询王五的学生的详细情况。

Select *    From   Student  Where  Sname Like ‘王五’;

等价于:

Select  * From   Student Where Sname=  ‘王五’;

【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升
2) 匹配模板为含通配符的字符串

[例13] 查询所有姓刘学生的姓名、学号和性别

Select Sname,Sno,SsexFrom  StudentWhere  Sname Like '王%';

【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升
[例14] 查询名字中第2个字为"五"字的学生的姓名和学号

Select Sname,SnoFrom  StudentWhere Sname Like '_五%';(Where Sname Like '_五_')   --这个是不对的哦,只查询名字为三个字中间为五的

【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升
    当用户要查询的字符串本身就含有 % 或 _ 时,要使用Escape ‘’ 短语对通配符进行转义,转义为普通字符。

1.1.2.2.5涉及空值的查询

[例15] 查所有有成绩为空的学生学号和课程号。

Select Sno,CnoFrom   SCWhere  Grade Is Not Null;
1.1.2.2.6多重条件查询

    用逻辑运算符 And 和 Or 来联结多个查询条件,And 的优先级高于 Or,可以用括号改变优先级,可用来实现多种其他谓词,[Not] IN,[Not] Between … And …。
[例16] 查询计算机系年龄在20岁以下的学生姓名

   Select  Sname   From   Student   Where Sdept= 'CS' And Sage<20;
1.1.2.2.7对查询结果排序

    用Order By子句,可以按一个或多个属性列排序,升序:ASC 降序:DESC 缺省值为升序,当排序列含空值时,ASC:排序列为空值的元组最先显示,DESC:排序列为空值的元组最后显示 。
[例17] 查询选修了103号课程的学生的学号及其成绩,查询结果按分数降序排列

  Select Sno,Grade  From   SC  Where  Cno= '3'  Order By Grade DESC; 
1.1.2.2.8使用集函数

5类主要集函数:
计数:
Count([ Distinct | All ] *)
Count([ Distinct | All ] )
计算总和:
Sum([ Distinct | All ]
计算平均值:
Avg([ Distinct | All ] )
求最大值:
Max([Distinct|All] )
求最小值:
Min([Distinct|All] )
Distinct短语:在计算时要取消指定列中的重复值
All短语:不取消重复值
All 为缺省值
[例17] 查询学生总人数

Select Count(*)From   Student;

[例18] 查询选修了课程的学生人数

Select Count (Distinct Sno)    --注:用Distinct以避免重复计算学生人数From  SC;

[例19] 计算1号课程的学生平均成绩。

Select Avg(Grade)From  SCWhere Cno= '1';

[例20] 查询选修1号课程的学生最高分数。

Select Max(Grade)From  SCWhere Cno= '1'; 
1.1.2.2.9对查询结果分组

    使用Group By子句分组 ,细化集函数的作用对象 ,未对查询结果分组,集函数将作用于整个查询结果,对查询结果分组后,集函数将分别作用于每个组 。Group By子句的作用对象是查询的中间结果表。分组方法:按指定的一列或多列值分组,值相等的为一组 。
[例21] 求各个课程号及相应的选课人数。

Select  Cno,Count(Sno)From    SCGroup By Cno;

使用Having短语筛选最终输出结果:只有满足Having短语指定条件的组才输出。
[例22] 查询选修了3门以上课程的学生学号,门数

Select Sno,sname,count(cno)From   SC,student where sc.sno=student.snoGroup By Sno,snameHaving  Count(cno) >3;

Having短语与Where子句的区别:
作用对象不同:
Where子句作用于基表或视图,从中选择满足条件的元组。
Having短语作用于组,从中选择满足条件的组。

    本期给大家带来的是Mysql的数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升,如有问题欢迎在下面评论区留言哦;下期博主给大家带来Mysql的数据操纵语法(SQL DML)-- 多表查询(SELECT)。

注:本文章仅用于参考学习,如有错误,请大家指正。

开发者涨薪指南 【Mysql 一周速成Mysql】 第三篇SQL语法 -- 数据操纵(SQL DML)-- 单表查询(SELECT)进阶提升 48位大咖的思考法则、工作方式、逻辑体系