版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/zijikanwa/article/details/80310703
1.1 事务的概念
- 事务:由一步或几步数据库操作序列组成的逻辑执行单元。
1.2 事务的4个特性(或ACID性)
- 原子性(Atomicity):要不全成功,要不全失败
- 一致性(Consistency):从一个一致性状态到达另外一个一致性状态
- 隔离性(Isolation):事务之间互不影响
- 持久性(Durability):事务提交后,能够持久性影响数据库。
1.3 事务隔离
1.3.1 事务隔离的概述
- 当多个线程都开启事务来操作数据库中的数据时,数据库系统要能进行隔离操作,以保证各个线程获取数据的准确性。
1.3.2 不事务隔离带来的问题
1. 更新丢失
- 对于同一数据,T1(写事务)和T2(写事务)同时更新;
- T1更新成功,T2更新失败回滚 –> 导致覆盖T1的更新。
2. 脏读
- T1(写事务)修改数据,但未提交;
- T2(读事务)读取了该数据;
- T1回滚事务 –> 导致T2读到的是脏数据。
3. 不可重复读义
- T1(读事务)读取某一数据;
- T2(写事务)修改了这一数据并提交;
- T1再次读取该数据 –>得到不同的结果
4. 幻读
- T1(读事务)读取某一范围的数据行;
- T2(写事务)又在该范围内插入了新行;
- T1再次读取该范围的数据行 –> 发现有新的”幻影”行。
1.3.3 事务的隔离级别
1. Read Uncommitted(读取未提交内容)
- 名称解释:可读取未提交的数据
- 含义解释:对于同一数据,一事务写时禁止其他写事务。
- 解决:”更新丢失”问题
2. Read Committed(读取提交内容)
- 名称解释:只有提交以后的数据才能被读取
- 含义解释:对于同一数据,一事务写时禁止其他读写事务。
- 解决:”脏读”,”更新丢失”问题
- 这是大多数数据库系统的默认隔离级别(但不是MySQL默认的)
3. Repeatable Read(可重复读)
- 名称解释:确保同一事务多次读取同一数据时,能看到同样的数据行。
- 含义解释:对于同一数据,一事务写时禁止其他事务读写,一事务读时禁止其他事务写。
- 解决:”不可重复读”,”更新丢失”和”脏读”问题
- 这是MySQL的默认事务隔离级别
4. Serializable(可串行化)
- 名称解释:它要求事务序列化执行,事务只能一个接着一个地执行,但不能并发执行。即限制所有读写事务都必须串行化实行。
- 一事务写时禁止其他事务读写,一事务读时禁止其他事务读写
- 解决:”幻读”,不可重复读”,”更新丢失”和”脏读”问题
- 这是最高的隔离级别,以锁表的方式使得其他的线程只能在锁外等待。
总结:各隔离级别对各种异常的控制能力
隔离级别 | 更新丢失 | 脏读 | 不可重复读 | 幻读 |
---|---|---|---|---|
RU(读未提交) | 避免 | |||
RC(读提交) | 避免 | 避免 | ||
RR(可重复读) | 避免 | 避免 | 避免 | |
S(串行化) | 避免 | 避免 | 避免 | 避免 |
1.3.4 常见数据库的事务隔离
- 常见数据库的默认事务隔离
数据库 | 默认级别 |
---|---|
MySQL | 可重复读(Repeatable Read) |
Oracle | 读提交(Read Committed) |
SQLServer | 读提交(Read Committed) |
2. 说明
1. 对于MySQL数据库
- 支持上面四种隔离级别,默认的为Repeatable read (可重复读);
- MySQL的Repeatable Read隔离级别也解决了幻读问题(通过*Next-key lock加锁方法即范围锁解决*不可重复读和幻读问题
- 如select * from t where a>10
会对key为[10,infinite)范围的行加锁,这样其他事务就不能对此范围内key对应的行更改)达到了SQL、SQL2标准中的Serializable级别。
2. 对于Oracle数据库
- 只支持Serializable (串行化)级别和Read committed (读已提交)这两种级别,其中默认的为Read committed级别。