SQL 面试
以下是常见的 SQL 面试题目,涵盖基础语法、高级查询、性能优化和实际应用场景,适合准备数据库相关的技术面试:
1. 基础语法
Q1: SQL 的 SELECT
语句基本结构是什么?
SELECT column1, column2 -- 选择列
FROM table_name -- 数据来源
WHERE condition -- 过滤条件
GROUP BY column -- 分组
HAVING group_condition -- 分组后过滤
ORDER BY column -- 排序
LIMIT n; -- 限制返回行数
Q2: WHERE
和 HAVING
的区别?
WHERE | HAVING |
---|---|
过滤 行(在分组前应用) | 过滤 分组(在 GROUP BY 后应用) |
不能使用聚合函数(如 SUM , COUNT ) | 必须搭配聚合函数使用 |
示例:WHERE salary > 5000 | 示例:HAVING COUNT(orders) > 10 |
2. 表操作与约束
Q3: 如何创建带约束的表?
CREATE TABLE employees (
id INT PRIMARY KEY, -- 主键
name VARCHAR(50) NOT NULL, -- 非空
email VARCHAR(100) UNIQUE, -- 唯一
salary DECIMAL(10,2) CHECK (salary > 0), -- 检查约束
dept_id INT FOREIGN KEY REFERENCES departments(id) -- 外键
);
Q4: TRUNCATE
、DELETE
和 DROP
的区别?
命令 | 作用 | 是否可回滚 | 是否重置自增ID |
---|---|---|---|
DELETE | 删除数据(可带条件) | 是 | 否 |
TRUNCATE | 清空表(全删) | 否 | 是 |
DROP | 删除表(结构和数据) | 否 | - |
3. 高级查询
Q5: 如何实现多表连接(JOIN)?
- INNER JOIN(内连接)
SELECT users.name, orders.amount
FROM users
INNER JOIN orders ON users.id = orders.user_id; - LEFT JOIN(左连接,保留左表所有行)
- FULL OUTER JOIN(全外连接,保留所有行)
Q6: 子查询 vs 连接查询,如何选择?
- 子查询:适合简单逻辑,可读性高
SELECT name FROM users
WHERE id IN (SELECT user_id FROM orders WHERE amount > 100); - 连接查询:适合复杂关联,性能通常更好
4. 聚合与分组
Q7: 如何统计每个部门的平均工资?
SELECT
department,
AVG(salary) AS avg_salary
FROM employees
GROUP BY department;
Q8: GROUP BY
和 DISTINCT
的区别?
GROUP BY | DISTINCT |
---|---|
通常搭配聚合函数(如 AVG ) | 仅去重 |
示例:GROUP BY dept | 示例:SELECT DISTINCT dept |
5. 索引与性能优化
Q9: 什么是索引?如何创建?
- 索引:加速查询的数据结构(如 B-Tree)
- 创建语法:
CREATE INDEX idx_name ON employees(name);
CREATE UNIQUE INDEX idx_email ON users(email); -- 唯一索引
Q10: 索引的优缺点?
- 优点:加速
WHERE
、JOIN
、ORDER BY
- 缺点:降低写入速度(需维护索引),占用存储
6. 事务与锁
Q11: 什么是事务的 ACID 特性?
- Atomicity(原子性):事务要么全部完成,要么全部回滚
- Consistency(一致性):数据始终满足约束
- Isolation(隔离性):并发事务互不干扰
- Durability(持久性):事务提交后数据永久保存
Q12: 常见的隔离级别有哪些?
级别 | 脏读 | 不可重复读 | 幻读 |
---|---|---|---|
READ UNCOMMITTED | 可能 | 可能 | 可能 |
READ COMMITTED | 不可能 | 可能 | 可能 |
REPEATABLE READ | 不可能 | 不可能 | 可能 |
SERIALIZABLE | 不可能 | 不可能 | 不可能 |
7. 实际场景问题
Q13: 如何优化慢查询?
- 使用
EXPLAIN
分析执行计划 - 添加合适的索引
- 避免
SELECT *
,只查询必要字段 - 优化
JOIN
条件(小表驱动大表)
Q14: 如何处理重复数据?
- 删除重复行(保留一行):
DELETE FROM users
WHERE id NOT IN (
SELECT MIN(id) FROM users GROUP BY email
);
8. 常用聚合函数与窗口函数(高级)
在 PostgreSQL 中,聚合函数(Aggregate Functions)和窗口函数(Window Functions)是非常强大的工具,用于进行复杂的数据分析和处理。这些函数使得数据查询更加灵活和高效。
聚合函数 Aggregate Functions
- COUNT: 计算行数。
SELECT COUNT(*) FROM table_name;
- SUM: 计算某列的总和。
SELECT SUM(column_name) FROM table_name;
- AVG: 计算某列的平均值。
SELECT AVG(column_name) FROM table_name;
- MAX: 找出某列的最大值。
SELECT MAX(column_name) FROM table_name;
- MIN: 找出某列的最小值。
SELECT MIN(column_name) FROM table_name;
- ARRAY_AGG: 将一组值合并为一个数组。
SELECT ARRAY_AGG(column_name) FROM table_name;
- STRING_AGG: 将一组字符串值连接成一个单一的字符串。
SELECT STRING_AGG(column_name, ', ') FROM table_name;
- STDDEV: 计算标准偏差。
SELECT STDDEV(column_name) FROM table_name;
窗口函数 Window Functions
窗口函数用于数据的分区,允许进行每个分区的聚合计算,而不是整个结果集。
- ROW_NUMBER: 对每个分区内的行进行编号。
SELECT ROW_NUMBER() OVER (PARTITION BY column_name ORDER BY another_column) FROM table_name;
- RANK: 对结果进行排名,相同值会有相同的排名,但会跳过随后的排名。
SELECT RANK() OVER (PARTITION BY column_name ORDER BY another_column) FROM table_name;
- DENSE_RANK: 与 RANK 类似,但不会跳过任何排名。
SELECT DENSE_RANK() OVER (PARTITION BY column_name ORDER BY another_column) FROM table_name;
- NTILE: 将分区的数据分成指定数量的近似大小的组。
SELECT NTILE(number_of_tiles) OVER (PARTITION BY column_name ORDER BY another_column) FROM table_name;
- LEAD: 获取当前行的下一行的值。
SELECT LEAD(column_name) OVER (ORDER BY another_column) FROM table_name;
- LAG: 获取当前行的上一行的值。
SELECT LAG(column_name) OVER (ORDER BY another_column) FROM table_name;
- FIRST_VALUE: 获取分区内的第一个值。
SELECT FIRST_VALUE(column_name) OVER (PARTITION BY another_column) FROM table_name;
- LAST_VALUE: 获取分区内的最后一个值。
SELECT LAST_VALUE(column_name) OVER (PARTITION BY another_column) FROM table_name;
这些函数使得在数据库级别上执行复杂的数据处理和分析成为可能,提高了效率并减少了将大量数据加载到应用层的需要。特别是在处理大型数据集时,这些函数非常有用。
Q15: 如何计算每个部门的工资排名?
SELECT
name,
department,
salary,
RANK() OVER (PARTITION BY department ORDER BY salary DESC) AS dept_rank
FROM employees;
9. 开启插件
SELECT * FROM pg_extension;
CREATE EXTENSION vector;
总结
分类 | 高频考点 |
---|---|
基础语法 | SELECT 、WHERE 、GROUP BY 、JOIN |
表操作 | 约束、DELETE vs TRUNCATE |
高级查询 | 子查询、聚合函数、窗口函数 |
性能优化 | 索引、EXPLAIN 、慢查询优化 |
事务 | ACID、隔离级别、锁机制 |
掌握这些问题可以覆盖 90% 的 SQL 面试考点!建议配合实际数据库(如 MySQL、PostgreSQL)练习。