事务隔离级别

事务具有以下4个特性

ACID

A:原子性,事务中的一组操作,一起成功或一起失败

C:一致性,事务中的多个操作的数据,数据状态一致

I:隔离性,一个事务不会影响另一个事务中的数据

D:持久性,事务执行完后,落表

事务问题

脏写:后面的事务值覆盖了前一个事务内的值

脏读:事务B读到了事务A未提交的数据,事务A的数据可能回滚。

不可重复读:事务B内相同的查询语句在不同时刻查到的结果不同

幻读:事务读取到了其他事务新增的数据,主要说的是新增数据。

表锁/行锁

表锁 开销小,加锁快 ;  lock table t_user read(write)应用:数据迁移的时候可使用。

行锁 开销大,加锁慢,发生锁冲突的概率低,并发度高

隔离级别

  1. 读未提交 :事务A读取到了事务B内还未提交的数据,如果事务B之后发生了异常回滚,就会造成事务A脏读、脏写。
  2. 读已提交:事务A只能读取事务B已经提交的数据;解决了“读未提交”的脏读脏写问题;但是引入了新问题:事务A相同的查询语句,两次查询,由于事务B提交了数据,可能查到的结果不同,也就是不可重复读问题。
  3. 可重复读:事务A在本事务内执行相同的查询,得到的结果相同。该隔离级别是Mysql数据库默认的隔离级别,底层使用了MVCC机制解决了“读已提交”的不可重复读问题,MVCC可参看我上编文章https://blog.csdn.net/weixin_37545216/article/details/122052249?spm=1001.2014.3001.5501icon-default.png?t=LA92https://blog.csdn.net/weixin_37545216/article/details/122052249?spm=1001.2014.3001.5501如果事务A内执行了次查询,比如 select  * from t_user where id <10 ,得到了2条数据,id=1 和id=5;之后事务B提交了id=3的数据,由于MVCC机制,事务A还是只能查到id=1 和id=5的数据,符合重复读的表现;但是如果事务A还执行了 update t_user set salary=salary+10 where id < 10,则事务A再执行刚才相同的查询语句,得到了id是【1,3,5】的数据,此时事务A懵逼了,以为自己产生了幻觉。所以“可重复读”隔离级别无法避免“幻读”问题。
  4. 串行化:对表所有的操作,包括查询都加锁,可避免幻读问题。但是性能很差,几乎没有使用。

解决幻读问题,还可使用“间隙锁”和“临近锁”;

在可重复读隔离级别下,假如有 id=1,id=2, id=3,id=7,id=8,id=11 这6条数据,如果有条查询语句:select * from t_user where id >5 and id < 10,那么where后面的范围与数据库中记录间隙([3,7],[8,11])有交集的部分都会加上锁,也就是 (3,7) 和 (8,11)区间的数据都会加上锁,其他事务不能操作这些数据,这就是间隙锁。

同时 id >= 11的部分也会加锁,即临近区间的部分也会加上,这就是临近锁。

事务注解

@Transaction 注解事务适用于流程很短,执行很快的方法上。否则会导致数据库吞吐量降低

而如果方法很长,且方法里还调用了其他很多无需事务的方法时候,最好不用注解事务@Transaction,而用编程事务(下图)

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值