## 数据库相关知识 ### 范式理论 范式理论是设计关系型数据库中二维表的指导思想。 1. 第一范式:数据表的每个列的值域都是由原子值组成的,不能够再分割。 2. 第二范式:数据表里的所有数据都要和该数据表的键(主键与候选键)有完全依赖关系。 3. 第三范式:所有非键属性都只和候选键有相关性,也就是说非键属性之间应该是独立无关的。 > **说明**:实际工作中,出于效率的考虑,我们在设计表时很有可能做出反范式设计,即故意降低方式级别,增加冗余数据来获得更好的操作性能。 ### 数据完整性 1. 实体完整性 - 每个实体都是独一无二的 - 主键(`primary key`) / 唯一约束(`unique`) 2. 引用完整性(参照完整性)- 关系中不允许引用不存在的实体 - 外键(`foreign key`) 3. 域(domain)完整性 - 数据是有效的 - 数据类型及长度 - 非空约束(`not null`) - 默认值约束(`default`) - 检查约束(`check`) > **说明**:在 MySQL 8.x 以前,检查约束并不起作用。 ### 数据一致性 1. 事务:一系列对数据库进行读/写的操作,这些操作要么全都成功,要么全都失败。 2. 事务的 ACID 特性 - 原子性:事务作为一个整体被执行,包含在其中的对数据库的操作要么全部被执行,要么都不执行 - 一致性:事务应确保数据库的状态从一个一致状态转变为另一个一致状态 - 隔离性:多个事务并发执行时,一个事务的执行不应影响其他事务的执行 - 持久性:已被提交的事务对数据库的修改应该永久保存在数据库中 3. MySQL 中的事务操作 - 开启事务环境 ```SQL start transaction ``` - 提交事务 ```SQL commit ``` - 回滚事务 ```SQL rollback ``` 4. 查看事务隔离级别 ```SQL show variables like 'transaction_isolation'; ``` ``` +-----------------------+-----------------+ | Variable_name | Value | +-----------------------+-----------------+ | transaction_isolation | REPEATABLE-READ | +-----------------------+-----------------+ ``` 可以看出,MySQL 默认的事务隔离级别是`REPEATABLE-READ`。 5. 修改(当前会话)事务隔离级别 ```SQL set session transaction isolation level read committed; ``` 重新查看事务隔离级别,结果如下所示。 ``` +-----------------------+----------------+ | Variable_name | Value | +-----------------------+----------------+ | transaction_isolation | READ-COMMITTED | +-----------------------+----------------+ ``` 关系型数据库的事务是一个很大的话题,因为当存在多个并发事务访问数据时,就有可能出现三类读数据的问题(脏读、不可重复读、幻读)和两类更新数据的问题(第一类丢失更新、第二类丢失更新)。想了解这五类问题的,可以阅读我发布在 CSDN 网站上的[《Java面试题全集(上)》](https://blog.csdn.net/jackfrued/article/details/44921941)一文的第80题。为了避免这些问题,关系型数据库底层是有对应的锁机制的,按锁定对象不同可以分为表级锁和行级锁,按并发事务锁定关系可以分为共享锁和独占锁。然而直接使用锁是非常麻烦的,为此数据库为用户提供了自动锁机制,只要用户指定适当的事务隔离级别,数据库就会通过分析 SQL 语句,然后为事务访问的资源加上合适的锁。此外,数据库还会维护这些锁通过各种手段提高系统的性能,这些对用户来说都是透明的。想了解 MySQL 事务和锁的细节知识,推荐大家阅读进阶读物[《高性能MySQL》](https://item.jd.com/11220393.html),这也是数据库方面的经典书籍。 ANSI/ISO SQL 92标准定义了4个等级的事务隔离级别,如下表所示。需要说明的是,事务隔离级别和数据访问的并发性是对立的,事务隔离级别越高并发性就越差。所以要根据具体的应用来确定到底使用哪种事务隔离级别,这个地方没有万能的原则。 ### 总结 关于 SQL 和 MySQL 的知识肯定远远不止上面列出的这些,比如 SQL 本身的优化、MySQL 性能调优、MySQL 运维相关工具、MySQL 数据的备份和恢复、监控 MySQL 服务、部署高可用架构等,这一系列的问题在这里都没有办法逐一展开来讨论,那就留到有需要的时候再进行讲解吧,各位读者也可以自行探索。