数据库事务隔离级别实例详解

1. 名词概念

1.1 脏读:一个事务,读取到另一个事务中没有提交的数据
1.2 不可重复读(虚读):在同一个事务中,两次读取到的数据不一样
1.3 幻读:一个事务操作(DML)数据表中所有记录,另一个事务添加了一条数据,第一个事务查询不到自己的修改

2. 隔离级别分类

2.1 read uncommitted:读未提交

问题:脏读、不可重复读、幻读

2.2 read committed:读已提交(Oracle默认)

问题:不可重复读、幻读

2.3 repeatable read:可重复读(MySQL默认)

问题:幻读

2.4 serializable:串行化

可以解决所有问题

3. 解析

3.1 设置read uncommitted时

当张三借钱给李四,设双方账号各有1000元,转账后张三变为500,李四变为1500

	事务1:						事务2:
		start transaction;				start transaction;
		张三:1000,李四:1000			        张三:1000,李四:1000
	转账后:
		张三:500,李四:1500

而张三进行转账操作时,开启事务,执行转账后,并未提交(commit)。由于设置了read uncommitted,李四可以查询到未提交的数据(脏读),看到账户余额为1500元,给张三打下500元借条。这时张三进行回滚(rollback),账户余额重新变为1000,李四再去看时账户余额已变为1000元(不可重复读

	事务1:									事务2:
	转账后:
		张三:500,李四:1500 (此时并未提交)   张三:500,李四:1500(其他事务未提交但能查看修改数据)
		rollback;
		(张三:1000,李四:1000)				张三:1000,李四:1000

此时张三一分钱没少,反而李四欠张三500元,这就出问题了

3.2 设置read committed时

此时不会发生3.1 所述问题,当张三转账完,执行 commit 提交后,张三账户余额为500元,李四账户余额为1500元

	事务1:							事务2:
	转账后:
		张三:500,李四:1500(未提交)		张三:1000,李四:1000(其他事务未提交不能查看修改数据)
		commit;
		(张三:500,李四:1500)			张三:500,李四:1500(其他事务已提交可以查看修改数据)

对于李四来说,第一次查看账户余额为1000元,第二次查看账户余额为1500元。在同一个事务中,两次读取到的数据不一样(不可重复读

		李四:1000
		李四:1500

从操作层面来说很合理,但是有些情况需要在同一个事务中读取到的数据都一样。例如做一个利率年增长查询,你查看到的是25%,而当你报告给你的上级说是25%时,你的上级一查看到的却是24.6%,同一个事务中查到的数据不一样。这时候就显得你工作有问题。此时我们需要定义repeatable read(可重复读)

3.3 设置repeatable read

此时我们开启一个事务,无论其他事务做了什么修改,只要我们本事务不提交(commit),即不重新开启事务,查询到的结果都是一样,不会改变。只有当我们提交事务后,再次开启事务,查询到的才是这次事务现在的数据

	事务1:					事务2:
		start transaction;			start transaction;
		张三:1000,李四:1000			张三:1000,李四:1000
	转账后:
		张三:500,李四:1500			张三:1000,李四:1000
		commit;
		(张三:500,李四:1500)		张三:1000,李四:1000(其他事务已提交,但查询结果不变)
										commit;
										start transaction;
										张三:500,李四:1500(重新开启事务查询)

但此时又有一个问题,当一个事务进行修改后,另一个事务中查询不到修改的记录(幻读

3.4 设置serializable

serializable相当于的概念,即一个事务在操作一个表的数据时,其他事务是不可以操作这张表的。只有当这个事务结束后,其他事务才可以操作

	事务1:					事务2:
		start transaction;			start transaction;
		张三:1000,李四:1000			等待
	转账后:
		张三:500,李四:1500			等待
		commit;
		(张三:500,李四:1500)		张三:500,李四:1500(查询到)

由此可见,事务隔离级别越高,效率也越低

posted @ 2022-12-21 14:42  凡223  阅读(10)  评论(0编辑  收藏  举报