Mysql查询语句时候一共分为以下几步,其中每一个操作都会产生一张虚拟的表,这个虚拟的表作为一个处理的输入,只是这些虚拟的表对用户来说是透明的,但是只有最后一个虚拟的表才会被作为结果返回。
语句执行顺序 :
顺序名称内容
1
SELECT
命令发起
2
* 或 AVG(字段)等
查询内容
3
FROM
查询位置
4
WHERE
条件查询
5
GROUP BY
分组
6
HAVING
筛选
7
ORDER BY (ASC/DESC)
排序
8
LIMIT
限制结果数
1、单表查询
查询指定的列
--在学生表中查询学号、姓名;
select sno, sname from student ;
查询全部列
--查询学生表中全部信息
select*from student;
对查询后的列进行 起别别名
--查询全部学生的“姓名”及其“出生年”两列
select sname as 姓名,(2017-Sage) as 出生年 from student;
单条件查询
--查询职位是 salesman 的记录;
select * from emp where job='Salesman'
多条件查询
--查询部门在10 或 20 的记录
select * from emp where deptno=10 or deptno=20;--查询部门在10的 或者部门在20且薪水小于2000的记录
select * from emp where deptno=10 or (deptno=20 and sal<=2000);
去重查询 ,使用 语句
--查询选修了课程的学生学号
select distinct sno as 选修了课程的学生学号 from score;
查询空值(NULL)
--查询没有先修课的课程号和课程名。
select Cno as 课程号,Cname as 课程名,Cpno from course where Cpno is null;--查询所有有成绩的学生学号、课程号及成绩
select Sno as 学号,Cno as 课程号,Grade as 成绩 from SC where Grade is not null;
将NULL转化为实际值 ,使用 语句
--查询津贴为NULL ,替换为0
select coalesce(comm,0) from emp;
模糊查询 (LIKE % _ 语句) %表示任意字符;_表示单个字符
--查询员工姓名以a开头的记录
select * from emp where ename like 'a%';--查询员工姓名中包含a的记录
select * from emp where ename like '%a%';--查询员工姓名第二个字母以a开头的记录
select * from emp where ename like '_a%';
2、分组查询
GROUP BY 语句根据一个或多个列对结果集进行分组。
在分组的列上我们可以使用 COUNT, SUM, AVG,等函数。
--查询每个部门的薪水总和
select deptno,sum(sal) from emp group bydeptno;--查询每个部门的津贴总和,空值不计算
select deptno,sum(comm) from emp group bydeptno;--查询每个部门的津贴总和,空值替换为0
select deptno,sum(coalesce(comm,0)) from emp group bydeptno;--查询每个部门的薪水在2000以上的总和
select deptno,sum(sal) from emp where sal>2000 group bydeptno;--查询每个部门、每个职业的薪水总和
select deptno,job,sum(sal) from emp group by deptno,job;
3、排序查询
使用 MySQL 的 ORDER BY 子句来设定你想按哪个字段哪种方式来进行排序,再返回搜索结果。
使用 ASC 或 DESC 关键字来设置查询结果是按升序或降序排列。 默认情况下,它是按升序排列。
--将薪水从小到大升序排列;
select * from emp order bysal;--将薪水从大到小降序排列;
select * from emp order by sal desc;--查询薪水最高的前5名的记录;
select * from emp order by sal desc limit 5;--查询每个部门 每个职务薪水总和的排名;
select deptno,job,sum(sal) as new_sal from emp group by deptno,job order by deptno,new_sal;
4、逻辑查询
逻辑操作符:
and \ or 且 或
!= (<>) 不等于
is null 查询空值
like 模糊查询
between ……and (a>=b and a
逻辑表达式:
case when ``` else ``` end语句
--查看每个员工的薪水,且将2000以下标为过低,4000以上标为过高,其余为可行
select ename,sal,case when sal<= 2000 then '过低'
when sal>= 4000 then '过高'
else '可行'
end asstatusfromemp;--查看每个员工编号、员工姓名,将薪水低于1000标为1,高于2000标为2
select empno,ename,case when sal >= 1000 and sal<2000 then 1
else 2
end asclassfrom emp order by class;
5、HAVING查询
having字句可以让我们筛选成组后的各种数据,where字句在聚合前先筛选记录,也就是说作用在group by和having字句前。而 having子句在聚合后对组记录进行筛选。
--查询每个部门、职务、薪水总和,且只显示总和大于5000的
select deptno,job,sum(sal) from emp group by deptno,job having sum(sal)>5000;--同样的条件,如果用WHERE语句,只能写成如下
select deptno,job,new_sal from (select deptno,job,sum(sal) as new_sal from emp group by deptno,job) as a where new_sal>5000;
having和where的区别:
作用的对象不同。
WHERE 子句作用于表和视图,HAVING 子句作用于组。
WHERE 在分组和聚集计算之前选取输入行(因此,它控制哪些行进入聚集计算),
而 HAVING 在分组和聚集之后选取分组的行。
因此,WHERE 子句不能包含聚集函数; 因为试图用聚集函数判断那些行输入给聚集运算是没有意义的。
相反,HAVING 子句总是包含聚集函数。(严格说来,你可以写不使用聚集的 HAVING 子句, 但这样做只是白费劲。同样的条件可以更有效地用于 WHERE 阶段。)
这样比在 HAVING 里增加限制更加高效,因为我们避免了为那些未通过 WHERE 检查的行进行分组和聚集计算。
综上所述:having一般跟在group by之后,执行记录组选择的一部分来工作的,可以用聚合函数,如having sum(sal)>5000
where则是执行所有数据来工作的。