一 表的复杂查询:
在实际应用过程中需要执行复杂的数据统计,经常需要显示多张表的数据,进行联合查询获取结果。
1:数据统计关键字:
m a x , m i n , s u m , a v g , c o u n t 。 聚 合 函 数 , 函 数 中 可 以 是 ( 字 段 ) 或 ( 表 达 式 ) max, min, sum, avg, count。聚合函数,函数中可以是 (字段)或(表达式) max,min,sum,avg,count。聚合函数,函数中可以是(字段)或(表达式)
示例:基于 emp 表
max(最大值), min(最小值)
显示所有员工中的最高工资和最低工资:
SQL> select max(sal) as 最高工资, min(sal) as 最低工资 from emp;
最高工资 最低工资
---------- ----------
5000 800
显示所有员工中的最高年薪和最低年薪:
SQL> select max(sal*13+nvl(comm,0)*13) as 最高年薪, min(sal*13+nvl(comm,0)*13) as 最低年薪 from emp;
最高年薪 最低年薪
---------- ----------
65000 10400
sum(计算和), avg(平均)
显示所有员工平均工资和工资总和
SQL> select sum(sal) as 总工资, avg(sal) as 平均工资 from emp;
总工资 平均工资
---------- ----------
29025 2073.21428
平均工资精确到后2位:
- ROUND()函数是会将计算结果进行四舍五入的,如果所需要的值需要进行四舍五入,就可以选择这个函数,可以有一个参数,也可以有两个参数;如果有两个param,第一个是你的计算表达式,第二个是需要保留的小数位数。
- TRUNC()函数是不会将计算结果进行四舍五入的,如果所需要的值不需要进行四舍五入,就可以选择这个函数,可以有一个参数,也可以有两个参数;如果有两个param,第一个是你的计算表达式,第二个是需要保留的小数位数。
- TO_CHAR(A/B,‘FM99990.99’)
TO_CHAR()是一个格式化函数,第一个参数是计算表达式,第二个参数是指定格式化的格式,如果保留两位小数则小数点后写两个99,这里的数字9代表的数字,也是一个占位符,表示该位置上以后会是一个数字,为什么小数点前面会是一个0,而不是9,是因为如果计算结果小于1,那么只会显示小数点和小数点之后的部分,前面的0会忽略掉。
SQL> select sum(sal) as 总工资, round(avg(sal),2) as 平均工资 from emp;
总工资 平均工资
---------- ----------
29025 2073.21
SQL> select sum(sal) as 总工资, trunc(avg(sal),2) as 平均工资 from emp;
总工资 平均工资
---------- ----------
29025 2073.21
SQL> select sum(sal) as 总工资, to_char(avg(sal),'fm99990.99') as 平均工资 from emp;
总工资 平均工资
---------- ---------
29025 2073.21
SQL>
avg 函数会忽略为空(NULL)的值:
SQL> select * from emp;
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7369 SMITH CLERK 7902 1980-12-17 800.00 20
7499 ALLEN SALESMAN 7698 1981-02-20 1600.00 300.00 30
7521 WARD SALESMAN 7698 1981-02-22 1250.00 500.00 30
7566 JONES MANAGER 7839 1981-04-02 2975.00 20
7654 MARTIN SALESMAN 7698 1981-09-28 1250.00 1400.00 30
7698 BLAKE MANAGER 7839 1981-05-01 2850.00 30
7782 CLARK MANAGER 7839 1981-06-09 2450.00 10
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20
7839 KING PRESIDENT 1981-11-17 5000.00 10
7844 TURNER SALESMAN 7698 1981-09-08 1500.00 0.00 30
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20
7900 JAMES CLERK 7698 1981-12-03 950.00 30
7902 FORD ANALYST 7566 1981-12-03 3000.00 20
7934 MILLER CLERK 7782 1982-01-23 1300.00 10
14 rows selected
SQL> select avg(comm) from emp;
AVG(COMM)
----------
550
count (统计)
统计所有员工人数:
SQL> select count(*) as 总人数 from emp;
总人数
----------
14
count 也会忽略 null :
SQL> select count(comm) from emp;
COUNT(COMM)
-----------
4
显示工资最高的员工名称和工作岗位:
使用子查询:
SQL> select t.ename 姓名,t.job 岗位,t.sal 工资 from emp t where t.sal=(select max(sal) from emp);
姓名 岗位 工资
---------- --------- ---------
KING PRESIDENT 5000.00
SQL>
2 数据分组:
group by 和 having 子句。
group by 用于查询结果的分组统计。
having 限制(过滤)分组显示结果,必须和 group by 配对使用。
显示每个部门的平均工资和最高工资:
SQL> select round(avg(sal),2) 平均工资,max(sal) 最高工资,deptno 部门编号 from emp group by deptno;
平均工资 最高工资 部门编号
---------- ---------- --------
1566.67 2850 30
2175 3000 20
2916.67 5000 10
SQL>
如果不加分组函数 group by:
SQL> select round(avg(sal),2) 平均工资,max(sal) 最高工资,deptno 部门编号 from emp;
select round(avg(sal),2) 平均工资,max(sal) 最高工资,deptno 部门编号 from emp
ORA-00937: not a single-group group function
SQL>
执行出错:not a single-group group function (不是单组分组函数)。因为 round(avg(sal),2) 和 max(sal) 返回的是单个结果,是所有的平均工资和最高工资。 而 deptno 又有多个查询结果,无法对应前面统计出来的单个数据,导致无法查询和显示,逻辑上也执行不了。但是如果加上 group by deptno 就是按照 部门获取 每个部门的平均工资 和 最高工资,执行逻辑也符合要求。
显示每个部门的每种工作岗位的平均工资和最低工资,最高工资:
SQL> select round(avg(sal),2) 平均工资,max(sal) 最高工资,min(sal) 最低工资,deptno 部门编号,job 岗位 from emp group by deptno,job order by deptno;
平均工资 最高工资 最低工资 部门编号 岗位
---------- ---------- ---------- -------- ---------
1300 1300 1300 10 CLERK
2450 2450 2450 10 MANAGER
5000 5000 5000 10 PRESIDENT
3000 3000 3000 20 ANALYST
950 1100 800 20 CLERK
2975 2975 2975 20 MANAGER
950 950 950 30 CLERK
2850 2850 2850 30 MANAGER
1400 1600 1250 30 SALESMAN
9 rows selected
显示部门平均工资低于2000的部门和 它的平均工资:
SQL> select round(avg(sal),2) 平均工资,deptno 部门编号 from emp group by deptno; --所有部门平均工资
平均工资 部门编号
---------- --------
1566.67 30
2175 20
2916.67 10
SQL> select round(avg(sal),2) 平均工资,deptno 部门编号 from emp group by deptno having round(avg(sal),2)<2000; --having 筛选结果,注意不能用别名
平均工资 部门编号
---------- --------
1566.67 30
SQL>
数据分组总结:
- 分组函数 a v g ( . . . ) avg(...) avg(...) 只能出现在选择列表,having,order by 子句中。
- 如果在 s e l e c t select select 语句总包含 group by,having,order by。那么它们的顺序是: [1] group by,[2] having,[3]order by 。
- 在选择列中如果有列,表达式和分组函数,那么这些列和表达式必须有一个出现在group by 子句中,否则就会出错。
二 多表查询:
多表查询是基于两个或两个以上的表或视图的查询。
首先要明白多表查询笛卡尔积的问题: 下面举例说明
示例 基于 oracle 默认表 emp,dept
首先看两个表中的数据:
SQL> select * from emp;
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7369 SMITH CLERK 7902 1980-12-17 800.00 20
7499 ALLEN SALESMAN 7698 1981-02-20 1600.00 300.00 30
7521 WARD SALESMAN 7698 1981-02-22 1250.00 500.00 30
7566 JONES MANAGER 7839 1981-04-02 2975.00 20
7654 MARTIN SALESMAN 7698 1981-09-28 1250.00 1400.00 30
7698 BLAKE MANAGER 7839 1981-05-01 2850.00 30
7782 CLARK MANAGER 7839 1981-06-09 2450.00 10
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20
7839 KING PRESIDENT 1981-11-17 5000.00 10
7844 TURNER SALESMAN 7698 1981-09-08 1500.00 0.00 30
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20
7900 JAMES CLERK 7698 1981-12-03 950.00 30
7902 FORD ANALYST 7566 1981-12-03 3000.00 20
7934 MILLER CLERK 7782 1982-01-23 1300.00 10
14 rows selected
SQL> select * from dept;
DEPTNO DNAME LOC
------ -------------- -------------
10 ACCOUNTING NEW YORK
20 RESEARCH DALLAS
30 SALES CHICAGO
40 OPERATIONS BOSTON
SQL>
从上面查询结果可知:emp 表 14条数据,dept 表 4条数据。那么两个表在一条 sql 语句中查询会怎样呢?
SQL> select * from emp,dept;
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO DEPTNO DNAME LOC
----- ---------- --------- ----- ----------- --------- --------- ------ ------ -------------- -------------
7369 SMITH CLERK 7902 1980-12-17 800.00 20 10 ACCOUNTING NEW YORK
7499 ALLEN SALESMAN 7698 1981-02-20 1600.00 300.00 30 10 ACCOUNTING NEW YORK
7521 WARD SALESMAN 7698 1981-02-22 1250.00 500.00 30 10 ACCOUNTING NEW YORK
7566 JONES MANAGER 7839 1981-04-02 2975.00 20 10 ACCOUNTING NEW YORK
7654 MARTIN SALESMAN 7698 1981-09-28 1250.00 1400.00 30 10 ACCOUNTING NEW YORK
7698 BLAKE MANAGER 7839 1981-05-01 2850.00 30 10 ACCOUNTING NEW YORK
7782 CLARK MANAGER 7839 1981-06-09 2450.00 10 10 ACCOUNTING NEW YORK
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20 10 ACCOUNTING NEW YORK
7839 KING PRESIDENT 1981-11-17 5000.00 10 10 ACCOUNTING NEW YORK
7844 TURNER SALESMAN 7698 1981-09-08 1500.00 0.00 30 10 ACCOUNTING NEW YORK
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20 10 ACCOUNTING NEW YORK
7900 JAMES CLERK 7698 1981-12-03 950.00 30 10 ACCOUNTING NEW YORK
7902 FORD ANALYST 7566 1981-12-03 3000.00 20 10 ACCOUNTING NEW YORK
7934 MILLER CLERK 7782 1982-01-23 1300.00 10 10 ACCOUNTING NEW YORK
7369 SMITH CLERK 7902 1980-12-17 800.00 20 20 RESEARCH DALLAS
7499 ALLEN SALESMAN 7698 1981-02-20 1600.00 300.00 30 20 RESEARCH DALLAS
7521 WARD SALESMAN 7698 1981-02-22 1250.00 500.00 30 20 RESEARCH DALLAS
7566 JONES MANAGER 7839 1981-04-02 2975.00 20 20 RESEARCH DALLAS
7654 MARTIN SALESMAN 7698 1981-09-28 1250.00 1400.00 30 20 RESEARCH DALLAS
7698 BLAKE MANAGER 7839 1981-05-01 2850.00 30 20 RESEARCH DALLAS
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO DEPTNO DNAME LOC
----- ---------- --------- ----- ----------- --------- --------- ------ ------ -------------- -------------
7782 CLARK MANAGER 7839 1981-06-09 2450.00 10 20 RESEARCH DALLAS
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20 20 RESEARCH DALLAS
7839 KING PRESIDENT 1981-11-17 5000.00 10 20 RESEARCH DALLAS
7844 TURNER SALESMAN 7698 1981-09-08 1500.00 0.00 30 20 RESEARCH DALLAS
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20 20 RESEARCH DALLAS
7900 JAMES CLERK 7698 1981-12-03 950.00 30 20 RESEARCH DALLAS
7902 FORD ANALYST 7566 1981-12-03 3000.00 20 20 RESEARCH DALLAS
7934 MILLER CLERK 7782 1982-01-23 1300.00 10 20 RESEARCH DALLAS
7369 SMITH CLERK 7902 1980-12-17 800.00 20 30 SALES CHICAGO
7499 ALLEN SALESMAN 7698 1981-02-20 1600.00 300.00 30 30 SALES CHICAGO
7521 WARD SALESMAN 7698 1981-02-22 1250.00 500.00 30 30 SALES CHICAGO
7566 JONES MANAGER 7839 1981-04-02 2975.00 20 30 SALES CHICAGO
7654 MARTIN SALESMAN 7698 1981-09-28 1250.00 1400.00 30 30 SALES CHICAGO
7698 BLAKE MANAGER 7839 1981-05-01 2850.00 30 30 SALES CHICAGO
7782 CLARK MANAGER 7839 1981-06-09 2450.00 10 30 SALES CHICAGO
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20 30 SALES CHICAGO
7839 KING PRESIDENT 1981-11-17 5000.00 10 30 SALES CHICAGO
7844 TURNER SALESMAN 7698 1981-09-08 1500.00 0.00 30 30 SALES CHICAGO
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20 30 SALES CHICAGO
7900 JAMES CLERK 7698 1981-12-03 950.00 30 30 SALES CHICAGO
7902 FORD ANALYST 7566 1981-12-03 3000.00 20 30 SALES CHICAGO
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO DEPTNO DNAME LOC
----- ---------- --------- ----- ----------- --------- --------- ------ ------ -------------- -------------
7934 MILLER CLERK 7782 1982-01-23 1300.00 10 30 SALES CHICAGO
7369 SMITH CLERK 7902 1980-12-17 800.00 20 40 OPERATIONS BOSTON
7499 ALLEN SALESMAN 7698 1981-02-20 1600.00 300.00 30 40 OPERATIONS BOSTON
7521 WARD SALESMAN 7698 1981-02-22 1250.00 500.00 30 40 OPERATIONS BOSTON
7566 JONES MANAGER 7839 1981-04-02 2975.00 20 40 OPERATIONS BOSTON
7654 MARTIN SALESMAN 7698 1981-09-28 1250.00 1400.00 30 40 OPERATIONS BOSTON
7698 BLAKE MANAGER 7839 1981-05-01 2850.00 30 40 OPERATIONS BOSTON
7782 CLARK MANAGER 7839 1981-06-09 2450.00 10 40 OPERATIONS BOSTON
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20 40 OPERATIONS BOSTON
7839 KING PRESIDENT 1981-11-17 5000.00 10 40 OPERATIONS BOSTON
7844 TURNER SALESMAN 7698 1981-09-08 1500.00 0.00 30 40 OPERATIONS BOSTON
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20 40 OPERATIONS BOSTON
7900 JAMES CLERK 7698 1981-12-03 950.00 30 40 OPERATIONS BOSTON
7902 FORD ANALYST 7566 1981-12-03 3000.00 20 40 OPERATIONS BOSTON
7934 MILLER CLERK 7782 1982-01-23 1300.00 10 40 OPERATIONS BOSTON
56 rows selected
查询结果 56 条数据,仔细看这56 条数据发现没有一条数据是重复的。这 56 条数据是怎样来的呢?看下图:
select * from emp,dept; 这条语句,是 dept 表中的行数据逐条匹配 emp 表中的行数据 。如果反过来这样查询 select * from dept,emp; 就是 emp 表中的行数据逐条匹配 dept 表中的行数据 。
依次,可知 select * from emp,dept,salgrade; 这条三表查询的数据个数是:
e
m
p
(
14
)
∗
d
e
p
t
(
4
)
∗
s
a
l
g
r
a
d
e
(
5
)
=
280
条
数
据
emp(14)*dept(4)*salgrade(5)=280 条数据
emp(14)∗dept(4)∗salgrade(5)=280条数据
select * from emp,dept,salgrade;
... ...(省略中间数据)
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO DEPTNO DNAME LOC GRADE LOSAL HISAL
----- ---------- --------- ----- ----------- --------- --------- ------ ------ -------------- ------------- ---------- ---------- ----------
7782 CLARK MANAGER 7839 1981-06-09 2450.00 10 40 OPERATIONS BOSTON 5 3001 9999
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20 40 OPERATIONS BOSTON 5 3001 9999
7839 KING PRESIDENT 1981-11-17 5000.00 10 40 OPERATIONS BOSTON 5 3001 9999
7844 TURNER SALESMAN 7698 1981-09-08 1500.00 0.00 30 40 OPERATIONS BOSTON 5 3001 9999
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20 40 OPERATIONS BOSTON 5 3001 9999
7900 JAMES CLERK 7698 1981-12-03 950.00 30 40 OPERATIONS BOSTON 5 3001 9999
7902 FORD ANALYST 7566 1981-12-03 3000.00 20 40 OPERATIONS BOSTON 5 3001 9999
7934 MILLER CLERK 7782 1982-01-23 1300.00 10 40 OPERATIONS BOSTON 5 3001 9999
280 rows selected
在多表查询时如果没有任何条件就会出现笛卡尔积现象,但是这些数据并不是我们想要的,需要进行条件过滤。多表查询避免出现笛卡尔积,就是 - 查询条件不能少于表的个数-1
1: 查询员工工资,姓名和所在部门名称:
SQL> select t1.ename as 姓名,t1.sal as 工资,t2.dname as 部门 from emp t1,dept t2 where t1.deptno=t2.deptno;
姓名 工资 部门
---------- --------- --------------
CLARK 2450.00 ACCOUNTING
KING 5000.00 ACCOUNTING
MILLER 1300.00 ACCOUNTING
JONES 2975.00 RESEARCH
FORD 3000.00 RESEARCH
ADAMS 1100.00 RESEARCH
SMITH 800.00 RESEARCH
SCOTT 3000.00 RESEARCH
WARD 1250.00 SALES
TURNER 1500.00 SALES
ALLEN 1600.00 SALES
JAMES 950.00 SALES
BLAKE 2850.00 SALES
MARTIN 1250.00 SALES
14 rows selected
SQL>
查询部门编号为 20 的 部门名称,工资和姓名
SQL> select t1.ename as 姓名,t1.sal as 工资,t2.dname as 部门 from emp t1,dept t2 where t1.deptno=t2.deptno and t2.deptno=20;
姓名 工资 部门
---------- --------- --------------
SMITH 800.00 RESEARCH
JONES 2975.00 RESEARCH
SCOTT 3000.00 RESEARCH
ADAMS 1100.00 RESEARCH
FORD 3000.00 RESEARCH
查询员工名称,工资和工资级别:
SQL> select t1.ename as 姓名,t1.sal as 工资,t2.grade as 工资级别 from emp t1,salgrade t2 where t1.sal between t2.losal and t2.hisal;
姓名 工资 工资级别
---------- --------- ----------
SMITH 800.00 1
JAMES 950.00 1
ADAMS 1100.00 1
WARD 1250.00 2
MARTIN 1250.00 2
MILLER 1300.00 2
TURNER 1500.00 3
ALLEN 1600.00 3
CLARK 2450.00 4
BLAKE 2850.00 4
JONES 2975.00 4
SCOTT 3000.00 4
FORD 3000.00 4
KING 5000.00 5
14 rows selected
自连接 查询: 在同一张表进行多表查询
示例:查询 员工名为 ‘FORD’ 的 上级领导信息。
SQL> select * from emp where emp.empno=(select mgr from emp where emp.ename='FORD');
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7566 JONES MANAGER 7839 1981-04-02 2975.00 20
查询所有员工上级:
SQL> select t1.ename as 员工,t2.ename as 上级 from emp t1, emp t2 where t1.mgr=t2.empno;
员工 上级
---------- ----------
FORD JONES
SCOTT JONES
TURNER BLAKE
ALLEN BLAKE
WARD BLAKE
JAMES BLAKE
MARTIN BLAKE
MILLER CLARK
ADAMS SCOTT
BLAKE KING
JONES KING
CLARK KING
SMITH FORD
13 rows selected
SQL> select t1.ename as 员工,t2.ename as 上级 from emp t1, emp t2 where t1.mgr=t2.empno(+); --外连接,显示所有
员工 上级
---------- ----------
FORD JONES
SCOTT JONES
JAMES BLAKE
TURNER BLAKE
MARTIN BLAKE
WARD BLAKE
ALLEN BLAKE
MILLER CLARK
ADAMS SCOTT
CLARK KING
BLAKE KING
JONES KING
SMITH FORD
KING
14 rows selected
子查询: 是指 嵌套在其他 sql 语句中 的 select 查询语句,也称 嵌套查询。
查询 SMITH 同一部门的员工信息:
SQL> select * from emp where emp.deptno=(select deptno from emp where emp.ename='SMITH');
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7369 SMITH CLERK 7902 1980-12-17 800.00 20
7566 JONES MANAGER 7839 1981-04-02 2975.00 20
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20
7902 FORD ANALYST 7566 1981-12-03 3000.00 20
SQL> select * from emp where emp.deptno=(select deptno from emp where emp.ename='SMITH') and emp.ename<>'SMITH'; --排除自己
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7566 JONES MANAGER 7839 1981-04-02 2975.00 20
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20
7902 FORD ANALYST 7566 1981-12-03 3000.00 20
查询出部门编号为10 的工作(岗位)相同的员工的 姓名,岗位,工资和部门编号:
SQL> select t.ename 姓名,t.job 岗位,t.sal 工资,t.deptno 部门编号 from emp t where t.job in (select job from emp where deptno=10);
姓名 岗位 工资 部门编号
---------- --------- --------- --------
CLARK MANAGER 2450.00 10
BLAKE MANAGER 2850.00 30
JONES MANAGER 2975.00 20
KING PRESIDENT 5000.00 10
MILLER CLERK 1300.00 10
JAMES CLERK 950.00 30
ADAMS CLERK 1100.00 20
SMITH CLERK 800.00 20
8 rows selected
多行子查询中 all 操作符的使用: 比较所有数据是否符合条件
示例:查询比30号部门员工工资都高的员工信息
SQL> select * from emp where sal > all(select sal from emp where deptno=30); --写法1 使用 all
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7566 JONES MANAGER 7839 1981-04-02 2975.00 20
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20
7902 FORD ANALYST 7566 1981-12-03 3000.00 20
7839 KING PRESIDENT 1981-11-17 5000.00 10
SQL> select * from emp where sal > (select max(sal) from emp where deptno=30); --写法2 使用 max
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7566 JONES MANAGER 7839 1981-04-02 2975.00 20
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20
7839 KING PRESIDENT 1981-11-17 5000.00 10
7902 FORD ANALYST 7566 1981-12-03 3000.00 20
多行子查询中 any 操作符的使用: 比较其中任意一条符合条件
示例:查询员工信息 工资高于任意一个比30号部门员工工资
SQL> select * from emp where sal > any(select sal from emp where deptno=30); --写法1 使用 any
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7839 KING PRESIDENT 1981-11-17 5000.00 10
7902 FORD ANALYST 7566 1981-12-03 3000.00 20
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20
7566 JONES MANAGER 7839 1981-04-02 2975.00 20
7698 BLAKE MANAGER 7839 1981-05-01 2850.00 30
7782 CLARK MANAGER 7839 1981-06-09 2450.00 10
7499 ALLEN SALESMAN 7698 1981-02-20 1600.00 300.00 30
7844 TURNER SALESMAN 7698 1981-09-08 1500.00 0.00 30
7934 MILLER CLERK 7782 1982-01-23 1300.00 10
7521 WARD SALESMAN 7698 1981-02-22 1250.00 500.00 30
7654 MARTIN SALESMAN 7698 1981-09-28 1250.00 1400.00 30
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20
12 rows selected
SQL> select * from emp where sal > (select min(sal) from emp where deptno=30); --写法2 使用 min
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7499 ALLEN SALESMAN 7698 1981-02-20 1600.00 300.00 30
7521 WARD SALESMAN 7698 1981-02-22 1250.00 500.00 30
7566 JONES MANAGER 7839 1981-04-02 2975.00 20
7654 MARTIN SALESMAN 7698 1981-09-28 1250.00 1400.00 30
7698 BLAKE MANAGER 7839 1981-05-01 2850.00 30
7782 CLARK MANAGER 7839 1981-06-09 2450.00 10
7788 SCOTT ANALYST 7566 1987-04-19 3000.00 20
7839 KING PRESIDENT 1981-11-17 5000.00 10
7844 TURNER SALESMAN 7698 1981-09-08 1500.00 0.00 30
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20
7902 FORD ANALYST 7566 1981-12-03 3000.00 20
7934 MILLER CLERK 7782 1982-01-23 1300.00 10
12 rows selected
多列子查询:查询多个列的数据的子查询
示例:查询出与 ‘SMITH’ 部门和岗位完全相同的所有员工信息。
SQL> select * from emp where (deptno,job)=(select deptno,job from emp where ename='SMITH');
--注意 这中写法,在oracle 是支持的,在其他数据库就不一定,并且 条件数据的对应关系要一致
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ---------- --------- ----- ----------- --------- --------- ------
7369 SMITH CLERK 7902 1980-12-17 800.00 20
7876 ADAMS CLERK 7788 1987-05-23 1100.00 20