关联查询
从多张表中查询对应记录的信息,关联查询的重点在于这些表中的记录的对应关系,这个对应关系也称为连接条件。
select k.kname,k.sal,h.loc from k,h where k.depino=h.depino
表名也可以写别名.
当两张表名有同名字段时,select 子句中必须要明确指出指定该字段来自哪张表,在关联查询中,表名也可以添加别名们可以简化select 语句的复杂度。
SELECT k.name,h.name FROM employee_K k,employee_H h WHERE k.depino=h.depino
关联查询要添加连接条件,否则会产生笛卡尔积
笛卡尔积通常是一个无意义的结果集,它的记录数使所有参与查询的表的记录数乘积的结果。要避免出现,数据量大时极易出现内存溢出等现象。
N张表关联查询要有N-1个连接条件。
连接条件和过滤条件同时成立。
select k.kname,k.sal,h.loc from k,h where k.depino=h.depino and h.loc='shanghai'
内连接
join... on... 内连接返回所有满足连接条件的记录。不满足条件的不会被查询出来。
select k.kname,sal,h.loc from k h where k.depino=h.depino and sal>2000 select k.kname,sal,h.loc from k join h on k.depino=h.depino where sal>2000
连接条件和过滤条件分开,层次感更好,条理更清晰。
外连接
外连接除了会将满足连接条件的记录查询出来以外,还会将不满足的连接条件的记录也查询出来。
外连接分
左外连接:以 join 左侧表作为驱动表(所有数据都会被查询出来),那么该表中某条 记录不满足连接条件时,来自右侧表中的字段全部填null。
select k.name,h.name from k left outer join h on k.depino=h.depino select k.name,h.name from k join h on k.depino=h.depino(+)
右外连接
select k.name,h.name from k join h on k.depino(+)=h.depino
全外连接
select k.name,h.name from k full outer join h on k.depino=h.depino
自连接
自连接:当前一张表的一条记录可以对应当前表自己的多条记录。
自连接是为了解决同类型数据但是又存在上下级关系的树状结构数据时使用。
select k.kname,kk.kname from k ,k kk where k.id=kk.pid
自连接连接多个表
select k.kname,kk.kname,h.loc from k,k kk,h where k.pid=kk.id and kk.depino=h.depino and k.kname='bob' select k.kname,kk.kname,h.loc from k join k kk on k.pid=kk.id join h on kk.depino=h.depino where k.kname='bob'
子查询
子查询是一条select 语句,但是他嵌套在其他SQL语句中,为的是给其他SQL语句提供数据以支持其执行操作。
SELECT kname,sal FROM K WHERE sal>(select sal FROM k WHERE kname='ali')
在DDL中,根据子查询的结果集快速创建一张表。
创建表时如果字查询中的字段有别名则该表对应的字段就使用该别名作为其字段名,当子查询中一个字段名含有函数表达式,则必须要使用别名。
CREATE TABLE employee AS SELECT k.kname,k.sal,k.id,h.hname,h.loc FROM h,k WHERE k.depino=h.depino
在DML中使用子查询。
SELECT*FROM K WHERE depino=(SELECT depino FROM K WHERE kname='alcie' )
子查询在查询语句中的运用
select depino ,kname,sal from k where sal >(select avg(sal) from K)
- 单行单列子查询:常用于过滤条件,可以配合=,<+,<,>,>=使用
- 多行多列子查询:常用于过滤条件,由于查询出多个值,在判断=时,要用IN,
判断>,>=等操作,要用ALL,ANY。
- 多行多列子查询:当成一张表来看。
select kname,sal from k where sal >all(select sal from k where depino in(10,30))
exists,not exists 关键字
exists 后面跟一个子查询,当子查询可以查询出至少一条记录,则exists表达式成立并返回TRUE。
select kname,sal from k where exists(select *from k,h where k.depino=h.depino) select kname,sal from k where not exists (select *from h where k.depino=h.depino)
子查询语句在having子句中的使用。
select min(sal),depino from k GROUP BY depino having min(sal)>(select min(sal) from k where depino=30)
子查询在FROM子句中的运用
当一个子查询是多列子查询,通常将该子查询的结果集当做一张表看待并基于它进行二次查询。
select AVG(sal),depino from k group bu depino select kname,k.sal,depino from k,(select AVG(sal) avg_sal,depino from k group by depino) A where k.depino=A.depino and k.sal>A.avg_sal
子查询在select 子句中的使用。
可以将查询的结果当做外层查询记录中的一个字段值显示。
select kname,k.sal,(select hname from h where k.depino=h.ddepino) from k