1、要解决的实际问题
脏读
脏读就是读取到了数据库中不存在的或者读取到错误的数据, 原因:读取到其他事务没有提交的数据,因为没有提交,所以可能会存在回滚!导致数据改动。
幻读
幻读是针对数据**插入(INSERT)**操作来说的。假设事务A对某些行的内容作了更改,但是还未提交,此时事务B插入了与事务A更改前的记录相同的记录行,并且在事务A提交之前先提交了,而这时,在事务A中查询,会发现好像刚刚的更改对于某些数据未起作用,但其实是事务B刚插入进来的,让用户感觉很魔幻,感觉出现了幻觉,这就叫幻读。
重复读
在一个事务之内,查询到的数据始中都是相等的。针对的是更新操作。比如数据库里面又、有一条记录,在当前事务期间对它查询时,应该始终保持数据一致性。(在重复读, 允许其他事务插入数据)
不可重复度
对比可重复读,不可重复读指的是在同一事务内,不同的时刻读到的同一批数据可能是不一样的,可能会受到其他事务的影响,比如其他事务改了这批数据并提交了。通常针对数据**更新(UPDATE)**操作。
小结:不可重复读的和幻读很容易混淆,不可重复读侧重于修改,幻读侧重于新增或删除。解决不可重复读的问题只需锁住满足条件的行,解决幻读需要锁表
2、数据库事务概念
一个简单的事务介绍:你给你朋友转钱,从你账户扣钱和他账户价钱这两个操作必须全部执行成功,并且对数据修改完成, 如果有一操作失败,那必须回滚。
事务的特点:
- 原子性
- 隔离性
- 一致性
- 持久性
3、事务隔离级别
针对事务的隔离性有着不同的隔离级别 ,分别是:
- 读没提交:当前事务可以读取到其他事务没有提交的数据
- 读提交:当前事务只能读取到其他事务提交的数据
- 可重复读:在当前事务下读取到的数据必须一致
- 串行化:对于写操作,在其他事务没有提交时,它必须等待(单线程的那意思把 )
从上往下:隔离效果越来越好,性能的干扰越来越大。
四种隔离级别对问题的解决程度如下:
4、读未提交
事务A更新了数据,但是没有提交, 此时事务B在事务A 为提交之前查询得到了数据, 但事务A回滚了事务。很遗憾事务B将继续查询事务A回滚之前的脏数据。
5、读提交
事务A 对数据做出了更新, 但是一直未提交。未提交之前事务B不会查出更新的数据, 直到事务A 提交后事务B才会查到 更新后的数据。
这就出现了一个问题,在同一事务中(本例中的事务B),事务的不同时刻同样的查询条件,查询出来的记录内容是不一样的,事务A的提交影响了事务B的查询结果,这就是不可重复读,也就是读提交隔离级别。
6、可重复度
可重复是对比不可重复而言的,上面说不可重复读是指同一事物不同时刻读到的数据值可能不一致。而可重复读是指,事务不会读到其他事务对已有数据的修改,及时其他事务已提交,也就是说,事务开始时读到的已有数据是什么,在事务提交前的任意时刻,这些数据的值都是一样的。但是,对于其他事务新插入的数据是可以读到的,这也就引发了幻读问题。
7、串行化
事务A 还没有提交, 此时事务B 想要修改数据库, 则事务B不会被执行!!!它会陷入等待。等到事务A 提交后执行,等待期间可能会存在超时。
https://blog.csdn.net/m0_37752084/article/details/79942196
https://www.jianshu.com/p/4e3edbedb9a8
https://zhuanlan.zhihu.com/p/117476959
https://blog.csdn.net/xcy1193068639/article/details/85058641