mysql中员工表的查询_MySQL 4.1 高级查询之多表查询

高级查询之多表查询

一.前番回顾

1.基本函数

类似length,concat,substr,replace等字符串函数要多记,日期函数也是常常使用到的,毕竟有时候并不是简单地进行加减乘除四则运算。分组聚合函数则是进行分组查询的时候用到,而且一般来说聚合函数的应用场景比较多。

2.数据库完整性

主要分为实体完整性,域完整性和参照完整性

其中实体完整性包括:

​ 主键约束,唯一约束,主键自增

主键作为主要的索引字段,为用户提供高性能的查询,前提是每一条记录之间必须保证主键

非空和唯一,以及含唯一约束字段的唯一性。而主键自增则保证的是每次添加的记录在原有

添加的记录的主键的记录上保持每次+1的自增,此时不需要用户手动维护主键。

域完整性:

​ 非空约束

​ 默认值

相比于实体完整性对记录的约束,域完整性则指定到对应的字段,为用户在处理数据时,对

数据的添加做一个规定,要求非空,或者为其指定了默认值的字段,以实现自动补全那些

具有自己默认设置的信息数据。

引用(参照)完整性:

​ 外键约束

外键完整性主要体现在两表关联的情况,针对一对多,一对一,多对多的情况的进行主

键限制。

二.高级查询(一)

1.高级查询的分类

多表关联查询

子查询

联合查询

2.多表关联查询

定义:

所谓的多表关联查询即指:多张表进行联合查询。当然这些表可能一样,也可能不一样。说一样指的是多次对自身查询。

多表关联查询的分类:

内连接

自然连接

外连接

1) 内连接

两表进行内连接,即两张表通过关联字段进行连接,非公有字段进行拼接,而对于公有字段即关联字段,则是取其中一张表的,然后记录取的是关联字段值在两表中都有的记录。

在解释内连接之前首先看一个数学中的概念:笛卡尔积

参见百度:

两个集合X和Y的笛卡尓积(Cartesian product),又称直积,表示为X × Y,第一个对象是X的成员而第二个对象是Y的所有可能有序对的其中一个成员

上述表达的意思大概如图所示:

7dbb25c9783f

笛卡尔积.png

然后用SQL的表示形式如下:

数据准备:

emp员工表

7dbb25c9783f

emp表原始数据.png

dept部门表:

7dbb25c9783f

dept表原始数据.png

放上SQL执行:

select * from emp,dept;

执行结果如下:(总记录数:56条)

7dbb25c9783f

笛卡尔积执行结果.png

我们发现总记录数是:56条即14*4=56条,显然是直接交叉连接得到结果,数据本身没什么问题,但是按照实际的情况:一个员工(比如我们的7369号员工)应该在20号部门才对,但是结果中却是多个,而且还是所有部门的都有,显然不符合实际情况。

分析原因:

我们没有对这两个表建立关联,即一个员工应该关联对应的部门,也就是说我们需要通过deptno把两表连接起来,通过员工的deptno在dept部门表中去找对应的部门才对,对此有两种解决方案:其一,给定where条件让两张表的deptno保持一致,即现在的内连接;其二,通过emp员工表的deptno去关联dept部门表的deptno字段,即下文即将提到的外连接。

现在我们通过内连接方式去关联两表,以期解决上述问题:

先放上SQL:

-- 形式1

select * from emp,dept where emp.deptno=dept.deptno;

再来看看结果:

7dbb25c9783f

内连接方式执行结果.png

分析:

很明显的,数据记录条数减少了很多,后面的deptno两表都是一一对应的,这样我们就把那些脏数据去除掉了,这才是我们要的数据。

其实上述SQL还不是内连接的标准形式,标准形式如下:(inner join ... on)

-- 形式2 (标准)

select * from emp inner join dept on emp.deptno=dept.deptno;

另外一种专门针对等值的内连接语法格式:

-- 形式3(限制)

select * from emp inner join dept using(deptno); -- 等值连接

结论:

当我们需要对两表进行联查时,如果我们需要两表的数据和实际相符合,我们可以通过公共的字段把两张表关联起来即通过where条件限制起来。或者使用内连接标准的形式,采用inner join ...on。但是现在有一个问题是,部门表里面的40号部门没有员工,但是我需要看到,但是这里却没有显示。究其缘由,主要是内连接是通过关联字段进行连接,只取两表公有的记录得合并记录。

于是就出现了接下来将为大家呈现的是外连接的解决方案

练习:

# 查询所有员工的员工编号,员工名称,上级的名称 (员工名称sname,员工编号empno,

上级编号mgr)

2) 外连接

定义:所谓的外连接,即以其中一张表为主表,去关联从表,结果的生成是根据主表的记录关联字段来限定的,即拿着主表的关联字段去从表中去查,查到就进行关联合并,至于主表中没有、从表中有的字段值的记录是不生成在结果中的,反过来,主表中有的、从表中没有的,那么该记录关联的从表的部分的字段值填充为null。

分类:

左外连接

右外连接

接下来就为大家展示通过外连接的方式解决上述内连接所没有解决的问题:

先上SQL(左外连接):

select * from dept dp left join emp ep on dp.deptno=ep.deptno; -- 其中dp和ep只

是我给部门表和员工表气的别名(相当于小名)

执行结果如下:

7dbb25c9783f

左外连接方式执行结果.png

结果分析:

很显然,结果中增加了一条记录,即没有员工的部门,可能你会说,现在不是把部门放到了前面吗?这个无所谓,我换下你就可以了。

上SQL:

select ep.*,dp.deptno deptno2,dp.dname,dp.loc from dept dp left join emp ep

on dp.deptno=ep.deptno; -- 因为要制定输出顺序的话,需要使用ep.*,dp.*,但是这种表示因

为列名(deptno)一样是会报错的,所以这样写的,不影响结果输出

执行结果如下:

7dbb25c9783f

左外连接方式执行结果2.png

就这样需求满足了,其实这种左外连接的方式可以改写成对应的右外连接连接的形式,因为两者可以相互转换。左外连接转右外连接只需要将left改成right,然后把主表和从表交换位置即可,结果是一样的。

上SQL:

select ep.*,dp.deptno deptno2,dp.dname,dp.loc from emp ep right join dept dp

on dp.deptno=ep.deptno;

注:执行结果和上面一致,这里就不截图了。

练习:

# 查询超过所在部门平均工资的员工信息 (使用外连接实现)

3) 自然连接

需要注意的是这里的自然连接并不是新的连接方式,而是内连接的一种(等值连接),但是它拥有自己的关键字,因此特此分开。但是因为是等值连接,还有球名称一致,限制比较大,所以应用场景基本为零。

select * from emp natural join dept; -- 类似内连接的using形式,名称一致的字段进

行等值连接

下一节:子查询

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值