MySQL数据库教程(三)
连接查询
多个表联合起来取数据,这种跨表查询,被称为连接查询。
连接查询的分类
根据年代分类
SQL92:1992年的语法
SQL99:1999年的语法
根据表连接的方式分类
内连接:
等值连接
非等值连接
自连接
外连接:
左外连接(左连接)
右外连接(右连接)
笛卡尔积现象
在没有任何条件限制的情况下,多个表直接连接会出现笛卡尔积现象。
为了避免笛卡尔积现象,只需要在where后面加 表名.字段1
select 字段1,字段2 from 表1,表2 where 表1.共同字段=表2.共同字段;
注意:这种语法是SQL92语法。
内连接
等值连接
1 | select 字段1,字段2 from 表1 inner(可以省略) join 表2 on 表1.共同字段=表2.共同字段; |
注意:这是SQL99语法,并且以下也是
非等值连接
1 | select 字段1,字段2 from 表1 inner(可以省略) join 表2 on 表1.共同字段!=表2.共同字段; |
自连接
1 | select 字段1,字段2 from 表1 inner(可以省略) join 表1 on 表1.字段=表1.字段; |
技巧:一张表看成两张表
外连接
右连接
1 | select 字段1,字段2 from 表1 inner(可以省略) right join 表2 on 表1.共同字段=表2.共同字段; |
right表示将join关键字右边的表看成主表,主要是为了将这张表的数据全部查询出来,捎带着关联查询左边的表。
左连接
1 | select 字段1,字段2 from 表1 left join 表2 on 表1.共同字段=表2.共同字段; |
left表示将join关键字左边的表看成主表,主要是为了将这张表的数据全部查询出来,捎带着关联查询右边的表。
注意:join前面有个outer,outer可以省略,加上可读性强。
外连接查询条数一定大于等于内连接的查询条数。
多张表连接
1 | select |
注意:一条SQL语句中内连接和外连接可以混合,都可以出现。
子查询
子查询概述:select语句中嵌套select语句,被嵌套的select语句称为子查询。
子查询出现的位置:1
2
3
4
5
6select
(select)...
from
(select)...
where
(select)...
where中的子查询
案例:找出比最低工资高的员工姓名和工资
第一步:查询最低工资是多少1
select min(sal) from emp;
第二步:找出大于800的1
select ename,sal from emp where sql>800;
第三步:合并1
select ename,sal from emp where sal > (select min(sal) from emp);
from后面的子查询
注意:from后面的子查询,可以将子查询的查询结果当做一张临时表。(技巧)
案例:找出每个岗位的平均工资的薪资等级。
第一步:找出每个岗位的平均工资(按照岗位分组求平均值)1
select job,avg(sal) from emp group by job;(当成t表)
第二步:把以上的查询结果当做成一张真实存在的表 t 。1
select * from salrgrade;(当成s表)
第三步:t表和s表进行表连接,条件:1
t.avg(sal) between s.losal and s.hisal;
1
2
3
4
5
6
7
8select
t.*,s.grade
from
(select job,avg(sal) as avgsal from emp group by job) t
join
salgrade s
on
t.avgsal between s.losal and s.hisal;
select中的子查询
案例:找出每个员工的部门名称,要求显示员工名和部门名。1
2
3
4select
e.ename,(select d.dname from dept d where e.deptno = d.deptno) as dname
from
emp e;
注意:对于select后面的子查询来说,子查询只能返回一条语句结果,多于一条,就报错
union(合并)
union:合并查询结果集
union的效率高一些
案例:查询工作岗位是MANAGER和SALESMAN的员工。1
2
3select ename,job from emp where job = 'MANAGER'
union
select ename,job from emp where job = 'SALESMAN'
注意事项:union在进行结果集合并的时候,要求列数相同。(最好数据类型也一致,在MySQL中可以不一致,但是在oracle不可以)
limit(非常重要)
imit:将查询结果集的一部分取出来,通常使用在分页查询中。
limit的用法:
完整用法:limit startindx,length;
缺省用法:limit 5;(这是取前5)
startindx是起始下标(从0开始)
length是长度
比如:3到5
则limit 2,3;(2表示起始位置从下标2开始,就是第三条记录,3表示长度)
注意:MySQL中limit在order by之后执行。
通用分页
案例:每页显示三条记录。
第一页:limit 0,3 [0,1,2]
第二页:limit 3,3 [3,4,5]
第三页:limit 6,3 [6,7,8]
第四页:limit 9,3 [9,10,11]
每页显示pageSize条记录
第pageNo页:1
limit (pageNo - 1) * pageSize , pageSize;
执行顺序
1 | select |
执行顺序:from>>where>>group by>>having>>select>>order by>>limit