细枝末节
1. 子查询又叫内查询,是出现在其他语句中的SELECT语句
2. 与子查询对应的是主查询,又叫外查询
3. 子查询一般放在小括号中
4. 子查询一般放在条件右侧
5. 标量子查询一般搭配单行操作符:>,<,>=,<=,=,<>
6. 列子查询一般搭配多行操作符:IN,ANY/SOME,ALL
7. 子查询的执行优先于主查询执行,主查询的条件用到了子查询的结果
分类
按结果集的行列数
1. 标量子查询: 结果集为一行一列
2. 列子查询: 结果集为一列多行
3. 行子查询: 结果集为一行多列
4. 表子查询: 结果集为多行多列
按子查询出现位置
1. SELECT后面: 支持标量子查询
2. FROM后面: 支持表子查询
3. WHEREE或HAVING后面: 支持标量子查询,列子查询,行子查询
4. EXISTS后面: 支持表子查询
WHERE或HAVING后面
支持标量子查询,列子查询,行子查询
示例
查询工资比Abel高的员工信息
/* 1. 查询Abel的工资 */
SELECT salary
FROM emp
WHERE name = 'Abel';
/* 2. 查询salary>1中结果的员工信息 */
SELECT *
FROM emp
WHERE salary > (
SELECT salary
FROM emp
WHERE name = 'Abel'
);
查询最低工资大于50号部门最低工资的部门id及其最低工资
/* 1. 查询50号部门的最低工资 */
SELECT MIN(salary)
FROM emp
WHERE dept_id = 50;
/* 2. 查询每个部门的最低工资 */
SELECT MIN(salary), dept_id
FROM emp
GOURP BY dept_id;
/* 3. 在2的结果集上进行筛选,满足MIN(salary)>1中结果 */
SELECT dept_id, MIN(salary)
FROM emp
GROUP BY dept_id
HAVING MIN(salary) > (
SELECT MIN(salary)
FROM emp
WHERE dept_id = 50
);
列子查询(多行子查询)
示例
查询location_id是1400或1700的部门的所有员工姓名
/* 1. 查询location_id是1400或1700的部门 */
SELECT id
FROM dept
WHERE loc_id IN(1400, 1700);
/* 2. 在1的结果中查询所有员工姓名 */
SELECT name
FROM emp
WHERE dept_id IN(
SELECT id
FROM dept
WHERE loc_id IN(1400, 1700)
);
EXISTS后面
格式
/* 子查询有元素,结果为1;子查询无元素,结果为0 */
EXISTS(子查询)
示例
查询有员工的部门名
SELECT name
FROM dept
WHERE EXISTS(
SELECT *
FROM emp
WHERE dept.id = emp.dept_id
);