动力节点 mysql 郭鑫 34道经典的面试题三
1、第十五题
15.列出受雇日期早于其直接上级的所有员工编号、姓名、部门名称
思路一:第一步将emp a看成员工表,将emp b 看成领导表,员工表的mgr字段应该等于领导表的主键字段
mysql> select
e.empno,
e.ename
from
emp e
join
emp b
on
e.mgr = b.empno where
e.hiredate < b.hiredate;
+-------+-------+
| empno | ename |
+-------+-------+
| 7369 | SMITH |
| 7499 | ALLEN |
| 7521 | WARD |
| 7566 | JONES |
| 7698 | BLAKE |
| 7782 | CLARK |
| 7876 | ADAMS |
+-------+-------+
7 rows in set
第二步:显示上面员工的部门名称,将emp a员工表和dept d进行关联
mysql> select
d.dname,
e.empno,
e.ename
from
emp e
join
emp b
on
e.mgr = b.empno
join
dept d
on
e.deptno = d.deptno
where
e.hiredate < b.hiredate;
+------------+-------+-------+
| dname | empno | ename |
+------------+-------+-------+
| ACCOUNTING | 7782 | CLARK |
| RESEARCH | 7369 | SMITH |
| RESEARCH | 7566 | JONES |
| RESEARCH | 7876 | ADAMS |
| SALES | 7499 | ALLEN |
| SALES | 7521 | WARD |
| SALES | 7698 | BLAKE |
+------------+-------+-------+
7 rows in set
下面两个题主要考察下左连接和右连接
14.列出所有员工及领导的名字
mysql> select
e.ename,
b.ename as leadername
from
emp e
left join
emp b
on
e.mgr = b.empno;
+--------+------------+
| ename | leadername |
+--------+------------+
| SMITH | FORD |
| ALLEN | BLAKE |
| WARD | BLAKE |
| JONES | KING |
| MARTIN | BLAKE |
| BLAKE | KING |
| CLARK | KING |
| SCOTT | JONES |
| KING | NULL |
| TURNER | BLAKE |
| ADAMS | SCOTT |
| JAMES | BLAKE |
| FORD | JONES |
| MILLER | CLARK |
+--------+------------+
14 rows in set
下面考查右连接
16.列出部门名称和这些部门的员工信息,同时列出那些没有员工的部门
mysql> select
d.dname,
e.*
from
emp e
right join
dept d
on
e.deptno = d.deptno;
+------------+-------+--------+-----------+------+------------+------+------+--------+
| dname | EMPNO | ENAME | JOB | MGR | HIREDATE | SAL | COMM | DEPTNO |
+------------+-------+--------+-----------+------+------------+------+------+--------+
| ACCOUNTING | 7782 | CLARK | MANAGER | 7839 | 1981-06-09 | 2450 | NULL | 10 |
| ACCOUNTING | 7839 | KING | PRESIDENT | NULL | 1981-11-17 | 5000 | NULL | 10 |
| ACCOUNTING | 7934 | MILLER | CLERK | 7782 | 1982-01-23 | 1300 | NULL | 10 |
| RESEARCH | 7369 | SMITH | CLERK | 7902 | 1980-12-17 | 800 | NULL | 20 |
| RESEARCH | 7566 | JONES | MANAGER | 7839 | 1981-04-02 | 2975 | NULL | 20 |
| RESEARCH | 7788 | SCOTT | ANALYST | 7566 | 1987-04-19 | 3000 | NULL | 20 |
| RESEARCH | 7876 | ADAMS | CLERK | 7788 | 1981-05-23 | 1100 | NULL | 20 |
| RESEARCH | 7902 | FORD | ANALYST | 7566 | 1981-12-03 | 3000 | NULL | 20 |
| SALES | 7499 | ALLEN | SALESMAN | 7698 | 1981-02-20 | 1600 | 300 | 30 |
| SALES | 7521 | WARD | SALESMAN | 7698 | 1981-02-22 | 1250 | 500 | 30 |
| SALES | 7654 | MARTIN | SALESMAN | 7698 | 1981-09-28 | 1250 | 1400 | 30 |
| SALES | 7698 | BLAKE | MANAGER | 7839 | 1981-05-01 | 2850 | NULL | 30 |
| SALES | 7844 | TURNER | SALESMAN | 7698 | 1981-09-08 | 1500 | 0 | 30 |
| SALES | 7900 | JAMES | CLERK | 7698 | 1981-12-03 | 950 | NULL | 30 |
| OPERATIONS | NULL | NULL | NULL | NULL | NULL | NULL | NULL | NULL |
+------------+-------+--------+-----------+------+------------+------+------+--------+
15 rows in set
下面考查having的使用,如果使用了groupby对数据进行设置之后,还需要对数据结构进行限制需要使用having
17.列出至少有5个员工的所有部门
第一步:先求出每个部门有多少员工,将emp a和部门表 dept d表进行关联,条件是e.deptno=d.deptno
第二步:然后通过分组e.deptno,过来count(e.ename) >= 5
mysql> select
e.deptno,count(e.ename) as totalEmp
from
emp e
group by
e.deptno
having
totalEmp >= 5;
+--------+----------+
| deptno | totalEmp |
+--------+----------+
| 20 | 5 |
| 30 | 6 |
+--------+----------+
2 rows in set
这里比较关键:第一点 使用了group by 字段,select 后面的字段只能是group by后面的字段e.deptno和聚合函数对应的字段count(e.ename) as totalEmp
第二点:现在要对聚合函数的结果进行过滤,totalEmp字段不是数据库中的字段,不能使用where进行限制,只能使用having
接下来:考察的是子查询,子查询是在一个数据库表中
18.列出薪水比“SMITH”多的所有员工信息
第一步:首先求出是,smith的工资
第二步:然后求出工资高于simith的
mysql> select * from emp where sal > (select sal from emp where ename = 'SMITH');
+-------+--------+-----------+------+------------+------+------+--------+
| EMPNO | ENAME | JOB | MGR | HIREDATE | SAL | COMM | DEPTNO |
+-------+--------+-----------+------+------------+------+------+--------+
| 7499 | ALLEN | SALESMAN | 7698 | 1981-02-20 | 1600 | 300 | 30 |
| 7521 | WARD | SALESMAN | 7698 | 1981-02-22 | 1250 | 500 | 30 |
| 7566 | JONES | MANAGER | 7839 | 1981-04-02 | 2975 | NULL | 20 |
| 7654 | MARTIN | SALESMAN | 7698 | 1981-09-28 | 1250 | 1400 | 30 |
| 7698 | BLAKE | MANAGER | 7839 | 1981-05-01 | 2850 | NULL | 30 |
| 7782 | CLARK | MANAGER | 7839 | 1981-06-09 | 2450 | NULL | 10 |
| 7788 | SCOTT | ANALYST | 7566 | 1987-04-19 | 3000 | NULL | 20 |
| 7839 | KING | PRESIDENT | NULL | 1981-11-17 | 5000 | NULL | 10 |
| 7844 | TURNER | SALESMAN | 7698 | 1981-09-08 | 1500 | 0 | 30 |
| 7876 | ADAMS | CLERK | 7788 | 1981-05-23 | 1100 | NULL | 20 |
| 7900 | JAMES | CLERK | 7698 | 1981-12-03 | 950 | NULL | 30 |
| 7902 | FORD | ANALYST | 7566 | 1981-12-03 | 3000 | NULL | 20 |
| 7934 | MILLER | CLERK | 7782 | 1982-01-23 | 1300 | NULL | 10 |
+-------+--------+-----------+------+------------+------+------+--------+
13 rows in set
子查询2
21.列出在部门“SALES”<销售部>工作的员工的姓名,假定不知道销售部门的部门编号
select deptno from dept where dname = 'SALES';
+--------+
| deptno |
+--------+
| 30 |
+--------+ select ename from emp where deptno = (select deptno from dept where dname = 'SALES');
+--------+
| ename |
+--------+
| ALLEN |
| WARD |
| MARTIN |
| BLAKE |
| TURNER |
| JAMES |
子查询三:in
24.列出薪金等于部门30中员工的薪金的其它员工的姓名和薪金
select distinct sal from emp where deptno = 30;
+---------+
| sal |
+---------+
| 1600.00 |
| 1250.00 |
| 2850.00 |
| 1500.00 |
| 950.00 |
+---------+ select ename,sal from emp where sal in(select distinct sal from emp where deptno = 30) and deptno <> 30;
19.列出所有“CLERK”(办事员)的姓名及其部门名称,部门人数
这是一个比较综合的题目
1、第一步在emp a表中查询出那些人的job岗位是办事员
2、将emp a表和dept d表相关联就可以得到职位是办事员的emp对应的部门名称
3、查询出每个部门对应的员工总数
4、将第三步的查询结果作为一个临时表t与第二步的查询结果进行关联,关联条件是t.deptno = d.deptno
select
d.deptno,d.dname,e.ename
from
emp e
join
dept d
on
e.deptno = d.deptno
where
e.job = 'CLERK';
t1
+--------+------------+--------+
| deptno | dname | ename |
+--------+------------+--------+
| 10 | ACCOUNTING | MILLER | 3
| 20 | RESEARCH | SMITH | 5
| 20 | RESEARCH | ADAMS | 5
| 30 | SALES | JAMES | 6
+--------+------------+--------+ 求出每个部门的员工数量
select
e.deptno,count(e.ename) as totalEmp
from
emp e
group by
e.deptno;
t2
+--------+----------+
| deptno | totalEmp |
+--------+----------+
| 10 | 3 |
| 20 | 5 |
| 30 | 6 |
+--------+----------+ select
t1.deptno,t1.dname,t1.ename,t2.totalEmp
from
(select
d.deptno,d.dname,e.ename
from
emp e
join
dept d
on
e.deptno = d.deptno
where
e.job = 'CLERK') t1
join
(select
e.deptno,count(e.ename) as totalEmp
from
emp e
group by
e.deptno) t2
on
t1.deptno = t2.deptno; +--------+------------+--------+----------+
| deptno | dname | ename | totalEmp |
+--------+------------+--------+----------+
| 10 | ACCOUNTING | MILLER | 3 |
| 20 | RESEARCH | SMITH | 5 |
| 20 | RESEARCH | ADAMS | 5 |
| 30 | SALES | JAMES | 6 |
+--------+------------+--------+----------+
下面考查在select 后面两个聚合函数的事业
20.列出最低薪水大于1500的各种工作及从事此工作的全部雇员人数
第一步:求出每种工作岗位的最低薪水,并且最低薪水大于15000
第二步:在第一步的基础上求出雇员数量(count *)
第一步:先求出每种工作岗位的最低薪水
select
e.job,min(e.sal) as minsal
from
emp e
group by
e.job;
+-----------+---------+
| job | minsal |
+-----------+---------+
| ANALYST | 3000.00 |
| CLERK | 800.00 |
| MANAGER | 2450.00 |
| PRESIDENT | 5000.00 |
| SALESMAN | 1250.00 |
+-----------+---------+ select
e.job,min(e.sal) as minsal,count(e.ename) as totalEmp
from
emp e
group by
e.job
having
minsal > 1500;
+-----------+---------+
| job | minsal |
+-----------+---------+
| ANALYST | 3000.00 |
| MANAGER | 2450.00 |
| PRESIDENT | 5000.00 |
+-----------+---------+
+-----------+---------+----------+
| job | minsal | totalEmp |
+-----------+---------+----------+
| ANALYST | 3000.00 | 2 |
| MANAGER | 2450.00 | 3 |
| PRESIDENT | 5000.00 | 1 |
+-----------+---------+----------+
接下来是对上面知识点的全部的一个综合的复习
22.列出薪金高于公司平均薪金的所有员工,所在部门、上级领导、雇员的工资等级
相当的经典
第一步:求出薪金高于公司平均薪金的所有员工
第二步:把第一步的结果当成临时表t 将临时表t和部门表 dept d 和工资等级表salary s进行关联,求出员工所在的部门,雇员的工资等级等
关联的条件是t.deptno = d.deptno t.salary betweent s.lower and high;
第三步:求出第一步条件下的所有的上级领导,因为有的员工没有上级领导需要使用left join 左连接
第一步:求出公司的平均薪水
select avg(sal) as avgsal from emp;
+-------------+
| avgsal |
+-------------+
| 2073.214286 |
+-------------+ select
d.dname,
e.ename,
b.ename as leadername,
s.grade
from
emp e
join
dept d
on
e.deptno = d.deptno
left join
emp b
on
e.mgr = b.empno
join
salgrade s
on
e.sal between s.losal and s.hisal
where
e.sal > (select avg(sal) as avgsal from emp);
+------------+-------+------------+-------+
| dname | ename | leadername | grade |
+------------+-------+------------+-------+
| RESEARCH | JONES | KING | 4 |
| SALES | BLAKE | KING | 4 |
| ACCOUNTING | CLARK | KING | 4 |
| RESEARCH | SCOTT | JONES | 4 |
| ACCOUNTING | KING | NULL | 5 |
| RESEARCH | FORD | JONES | 4 |
+------------+-------+------------+-------+
23.列出与“SCOTT”从事相同工作的所有员工及部门名称
查询出SCOTT的工作岗位
select job from emp where ename = 'SCOTT';
+---------+
| job |
+---------+
| ANALYST |
+---------+ select
d.dname,
e.*
from
emp e
join
dept d
on
e.deptno = d.deptno
where
e.job = (select job from emp where ename = 'SCOTT');
+----------+-------+-------+---------+------+------------+---------+------+--------+
| dname | EMPNO | ENAME | JOB | MGR | HIREDATE | SAL | COMM | DEPTNO |
+----------+-------+-------+---------+------+------------+---------+------+--------+
| RESEARCH | 7788 | SCOTT | ANALYST | 7566 | 1987-04-19 | 3000.00 | NULL | 20 |
| RESEARCH | 7902 | FORD | ANALYST | 7566 | 1981-12-03 | 3000.00 | NULL | 20 |
+----------+-------+-------+---------+------+------------+---------+------+--------+
25.列出薪金高于在部门30工作的所有员工的薪金的员工姓名和薪金、部门名称
第一步:先找出部门30的最高薪水
select max(sal) as maxsal from emp where deptno = 30;
+---------+
| maxsal |
+---------+
| 2850.00 |
+---------+ select
d.dname,
e.ename,
e.sal
from
emp e
join
dept d
on
e.deptno = d.deptno
where
e.sal > (select max(sal) as maxsal from emp where deptno = 30);
+------------+-------+---------+
| dname | ename | sal |
+------------+-------+---------+
| ACCOUNTING | KING | 5000.00 |
| RESEARCH | JONES | 2975.00 |
| RESEARCH | SCOTT | 3000.00 |
| RESEARCH | FORD | 3000.00 |
+------------+-------+---------+
这个题很关键
26.列出在每个部门工作的员工数量、平均工资和平均服务期限
第一步:求出每个部门对应的所有员工,这里使用了右连接,保证显示所有的部门,但是有的部门不存在员工,但是也必须把所有的部门显示出来
第二步:在第一步的基础上求出所有员工的数量,这里因为有的部门员工是null,所有不能使用count(*),count(*)统计包含null,应该使用count(e.ename)
第三步:求出员工的平均工资,因为有的部门员工不存在,所以对应的工作也是null,这里需要null值做处理
用法说明
1
IFNULL(expr1,expr2)
如果 expr1 不是 NULL,IFNULL() 返回 expr1,否则它返回 expr2。
IFNULL()返回一个数字或字符串值,取决于它被使用的上下文环境。
第四步:
mysql> SELECT TO_DAYS(950501);
+---------------------------------------------------------+
| TO_DAYS(950501) |
+---------------------------------------------------------+
| 728779 |
+---------------------------------------------------------+
1 row in set (0.00 sec)
我们来看下面的代码
ount(*)对行的数目进行计算,包含NULL
count(column)对特定的列的值具有的行数进行计算,不包含NULL值。
select count(*) from test2 ;
select count(id) from test2 ;
select count(name) from test2 ;
select count(name) from test2 where name is null;
当运行结果我们可以得出:3,3,2,0,为什么呢?让我来解释一下。首先count(1)指的并不是计算1的个数,而是指表的第一个字段,如果第一个字段没有建立索引,他的效率是很低的;而且count(column name)默认查询的是指定字段非空的个数,如果你想查询数据的所有行数,恰巧指定字段又是一个可存在空库数据的字段,那么得到的数据就不会是期望的值。再来说一下count(),在上述的count(column name)查询方式中,如果指定的column为限制为非空,那么mysql会将上述表达式转化为count()来进行查询。所以如果想要查询数据大小,在mysql中建议使用count(*)来执行,含义明了,速度还快。
同理:
28.列出所有部门的详细信息和人数
这里因为用到了左连接,同上面的题目,因为使用到了右连接可能存在null值,统计人数的时候不能使用count(*),而要使用count(e.ename)字段的值
select
d.deptno,d.dname,d.loc,count(e.ename) as totalEmp
from
emp e
right join
dept d
on
e.deptno = d.deptno
group by
d.deptno,d.dname,d.loc;
+--------+------------+----------+----------+
| deptno | dname | loc | totalEmp |
+--------+------------+----------+----------+
| 10 | ACCOUNTING | NEW YORK | 3 |
| 20 | RESEARCH | DALLAS | 5 |
| 30 | SALES | CHICAGO | 6 |
| 40 | OPERATIONS | BOSTON | 0 |
+--------+------------+----------+----------+
29.列出各种工作的最低工资及从事此工作的雇员姓名
select
e.job,min(e.sal) as minsal
from
emp e
group by
e.job;
+-----------+---------+
| job | minsal |
+-----------+---------+
| ANALYST | 3000.00 |
| CLERK | 800.00 |
| MANAGER | 2450.00 |
| PRESIDENT | 5000.00 |
| SALESMAN | 1250.00 |
+-----------+---------+ 将以上查询结果当成临时表t(job,minsal)
select
e.ename
from
emp e
join
(select
e.job,min(e.sal) as minsal
from
emp e
group by
e.job) t
on
e.job = t.job
where
e.sal = t.minsal; +--------+
| ename |
+--------+
| SMITH |
| WARD |
| MARTIN |
| CLARK |
| SCOTT |
| KING |
| FORD |
+--------+
动力节点 mysql 郭鑫 34道经典的面试题三的更多相关文章
- 动力节点 mysql 郭鑫 34道经典的面试题二
13.有3个表S(学生表),C(课程表),SC(学生选课表) S(SNO,SNAME)代表(学号,姓名) C(CNO,CNAME,CTEACHER)代表(课号,课名,教师) SC(SNO,CNO,SC ...
- 动力节点 mysql 郭鑫 34道经典的面试题
DROP TABLE IF EXISTS `dept`; CREATE TABLE `dept` ( `DEPTNO` int(2) NOT NULL COMMENT '部门编号', `DNAME` ...
- 【转】 71道经典Android面试题和答案,重要知识点都包含了
,,面试题1. 下列哪些语句关于内存回收的说明是正确的? (b ) A. 程序员必须创建一个线程来释放内存 B.内存回收程序负责释放无用内存 C.内存回收程序允许程序员直接释放内存 ...
- 71道经典Android面试题和答案
,,面试题1. 下列哪些语句关于内存回收的说明是正确的? (b ) A. 程序员必须创建一个线程来释放内存 B.内存回收程序负责释放无用内存 C.内存回收程序允许程序员直接释放内存 ...
- 这十道经典Python笔试题,全做对算我输
经常有小伙伴学了Python不知道是否能去找工作,可以来看下这十道题检验你的成果: 1.常用的字符串格式化方法有哪些?并说明他们的区别 a. 使用%,语法糖 print("我叫%s,今年%d ...
- 75道经典AI面试题,我就想把你们安排的明明白白的!(含答案)
基础知识(开胃菜) Python 1.类继承 有如下的一段代码: class A(object): def show(self): print 'base show' class B(A): def ...
- 二十道经典C#面试题
1.在下面的代码中,如何引用命名空间fabulous中的great? namespace fabulous{// code in fabulous namespace}namespace super{ ...
- 100多道经典的JAVA面试题及答案解析
面向对象编程(OOP) Java是一个支持并发.基于类和面向对象的计算机编程语言.下面列出了面向对象软件开发的优点: 代码开发模块化,更易维护和修改. 代码复用. 增强代码的可靠性和灵活性. 增加代码 ...
- 50道经典的JAVA编程题(31-35)
50道经典的JAVA编程题(31-35),今天考完了java,在前篇博客里面贴出了题了,见:<今天考试的JAVA编程题>.考完了也轻松了,下个星期一还考微机原理呢,啥都不会,估计今天就做到 ...
随机推荐
- try catch finally return 轶事
最近阿里发布了java开发手册终极版,看到其中一条规约:[强制]不能在 finally 块中使用 return, finally 块中的 return 返回后方法结束执行,不会再执行 try 块中的 ...
- GNS3内网通过cloud与实际网络实现互连互通的实验(使用环回网口)
一.背景: 在GNS3内构建一个测试网络,该测试网络的设备能够通过cloud访问外部网络设备和Internet网,外部网络也能直接访问GNS3内网的设备. 考虑通过cloud上的环回口连接GNS3内网 ...
- Rocket - tilelink - RAMModel
https://mp.weixin.qq.com/s/9ccDTm6HytvfGN5R2CPoAQ 简单介绍RAMModel的实现. 1. 基本介绍 RAMModel用于定义内存 ...
- Rocket - util - LanePositionedQueue
https://mp.weixin.qq.com/s/yO_9Ec3S5-AosRVLpsBgOg 简单介绍基于通道位置的队列(LanePositionedQueue)的实现. 1. ...
- (Java实现) 有重复元素排列问题
有重复元素的排列问题 [问题描述] 设R={ r1, r2 , -, rn}是要进行排列的n个元素.其中元素r1, r2 , -, rn可能相同.试设计一个算法,列出R的所有不同排列. [编程任务] ...
- Java实现 LeetCode 64 最小路径和
64. 最小路径和 给定一个包含非负整数的 m x n 网格,请找出一条从左上角到右下角的路径,使得路径上的数字总和为最小. 说明:每次只能向下或者向右移动一步. 示例: 输入: [ [1,3,1], ...
- java实现子集和问题
1 问题描述 求n个正整数构成的一个给定集合A = {a1,a2,a3,-,an}的子集,子集的和要等于一个给定的正整数d.请输出所有符合条件的子集. 2 解决方案 2.1 全排列思想求解 方法1:首 ...
- java实现转方阵
/* 对一个方阵转置,就是把原来的行号变列号,原来的列号变行号 例如,如下的方阵: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 转置后变为: 1 5 9 13 2 6 ...
- 5.keras-Dropout剪枝操作的应用
keras-Dropout剪枝操作的应用 1.载入数据以及预处理 import numpy as np from keras.datasets import mnist from keras.util ...
- 指定web默认首页,导致访问路径的问题
今天写了一个登陆页面,登陆成功跳转时,url中的路径不对 这是目录结构 |-web |---login |-----login.jsp |---success |-----success.jsp 这是 ...