SQL 教程综合案例

2次阅读

sql综合案例重在整合建表约束、索引视图、查询逻辑与事务边界;建表需严控NULL与check边界,drop前须查依赖,where/group by/order by须遵执行顺序,分页宜用游标避免性能断崖,跨库需注意默认行为差异。

SQL 教程综合案例

SQL 综合案例不是语法砌,而是验证你能否把建表、约束、索引、视图、查询逻辑真正串起来用。

CREATE table 时怎么写约束才不翻车

很多人建表只写 PRIMARY KEY,结果插入数据时突然报错,比如 Violation of CHECK constraintCannot insert null——其实问题出在约束没对齐业务规则。

  • 主键和唯一约束必须明确字段是否允许 NULLStudentNo char(10) NOT NULL UNIQUEStudentNo CHAR(10) UNIQUE 更安全,后者允许多行 NULL(SQL 标准中 NULL != NULL
  • CHECK 要覆盖边界值:比如年级 GradeLevel TINYINT CHECK (GradeLevel BETWEEN 1 AND 12),漏掉 013 就可能被脏数据绕过
  • 外键 ON delete SET NULL 前,务必确认字段本身是 NULL 允许的(如 ClassID INT NULL),否则直接建表失败

DROP 之前必须想清楚“删的是什么”

DROP TABLE 看似简单,但它是不可逆的物理删除——不仅清空数据,还顺手干掉关联的索引、约束、触发器,甚至依赖它的视图也会失效。

  • 执行前先查依赖:select * FROM sys.dm_exec_referencing_entities('Students', 'Object')(SQL Server)或 SELECT * FROM INFORMATION_SCHEMA.VIEW_TABLE_USAGE(跨库通用)
  • DROP VIEW 不影响基表,但 DROP INDEX IX_Students_Name ON Students 会立刻让按姓名查变慢——别在高峰期删
  • mysql 没有 DROP ... CASCADE 对视图的自动清理,删表后记得手动 DROP VIEW,否则下次 CREATE VIEW 会报 Table doesn't exist

WHERE + GROUP BY + ORDER BY 的顺序陷阱

新手常以为“先过滤再分组最后排序”是直觉,但 SQL 执行顺序是固定的:FROM → WHERE → GROUP BY → HAVING → SELECT → ORDER BY。错放逻辑就会查不到想要的结果。

  • WHERE 不能用聚合函数(如 WHERE count(*) > 1 错!得用 HAVING
  • ORDER BY 引用别名没问题(SELECT Name AS student_name FROM Students ORDER BY student_name),但 WHERE 里不能写 student_name——它还没生成
  • MySQL 8.0+ 默认开启 sql_mode=ONLY_FULL_GROUP_BYSELECT Name, COUNT(*) FROM Students GROUP BY ClassID 会报错,因为 Name 不在 GROUP BY 里也不在聚合中

用 TOP / LIMIT / FETCH FIRST 做分页时的真实代价

TOP 3LIMIT 3 看似轻量,但在大数据集上做“第 N 页”,性能会断崖式下跌。

  • SQL Server 的 OFFSET 1000 ROWS FETCH NEXT 10 ROWS ONLY 要先跳过前 1000 行,哪怕只取 10 条,也是全扫描
  • MySQL LIMIT 10000,10 同理,跳过的 10000 行仍需参与排序(如果带 ORDER BY
  • 更稳的做法是“游标分页”:记录上一页最后一条的 idEnrollDate,下一页查 WHERE EnrollDate > '2025-01-01' ORDER BY EnrollDate LIMIT 10

综合案例最易忽略的,是事务边界和默认行为差异——比如 MySQL 的 timestamp 自动更新、SQL Server 的 GETDATE() 精度是毫秒、postgresqlnow() 带时区。同一套 SQL 换个库就出错,不是语法问题,是环境假设错了。

text=ZqhQzanResources