导航菜单

SQL 学习/子查询与视图
课程进度 69% · 第7/9章7/9章 · 标签 1/4
1

子查询类型与用法

子查询是嵌套在另一个SQL语句中的查询,可分为标量子查询、行子查询、表子查询和相关子查询。常与IN、EXISTS、ANY、ALL等关键字结合使用。

sql
1
-- 标量子查询(返回单值)
2
SELECT name FROM students
3
WHERE class_id = (
4
SELECT id FROM classes WHERE name = '高三一班'
5
);
6
 
7
-- 表子查询(作为临时表)
8
SELECT * FROM (
9
SELECT * FROM students WHERE age > 18
10
) t;
11
 
12
-- 行子查询(多字段比较)
13
SELECT * FROM students
14
WHERE (class_id, score) = (
15
SELECT class_id, MAX(score)
16
FROM students
17
GROUP BY class_id
18
LIMIT 1
19
);

📖相关子查询可引用外层表字段。标量子查询返回单个值,表子查询可当作临时表使用。子查询必须用括号包裹。

2

IN / EXISTS 用法

IN和EXISTS都用于判断是否存在关联数据,但执行效率和使用场景有所不同。

sql
1
-- IN:值在子查询结果集中
2
SELECT name FROM students
3
WHERE class_id IN (
4
SELECT id FROM classes WHERE grade = 3
5
);
6
 
7
-- NOT IN:值不在子查询结果集中
8
SELECT name FROM students
9
WHERE class_id NOT IN (
10
SELECT id FROM classes WHERE grade = 1
11
);
12
 
13
-- EXISTS:存在关联数据
14
SELECT name FROM students s
15
WHERE EXISTS (
16
SELECT 1 FROM scores sc
17
WHERE sc.student_id = s.id
18
);
19
 
20
-- NOT EXISTS:不存在关联数据
21
SELECT name FROM students s
22
WHERE NOT EXISTS (
23
SELECT 1 FROM scores sc
24
WHERE sc.student_id = s.id
25
);
26
 
27
-- ANY / ALL 比较
28
SELECT * FROM students
29
WHERE score > ALL (
30
SELECT score FROM students WHERE class_id = 1
31
);

EXISTS适合判断是否存在关联数据,查到即停,性能优于IN(大数据集时)。NOT IN注意NULL值问题,NOT EXISTS更安全。EXISTS 中 SELECT 1 只是习惯写法。