前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >MySQL 事务隔离级别 理论+实战分析

MySQL 事务隔离级别 理论+实战分析

作者头像
AI码师
发布2022-12-22 10:21:47
2430
发布2022-12-22 10:21:47
举报

B站搜索“乐哥聊编程“有本篇文章配套视频‍ https://www.bilibili.com/video/BV14e4y117uG

概念介绍

读未提交( Read Uncommitted )

A开启事务后,能够读取到B事务未提交的数据,当A事务根据数据做一些逻辑处理时,这时候B回滚了事务,就会导致A读到的是脏数据

读已提交( Read Committed )

A开启事务后,只能看到B在提交事务之后产生的更新数据,会有一个问题:A如果在B提交事务前后分别对同一条数据进行了查询,会发现前后不一致,这也就造成了不可重复读的问题

可重复读( Repeatable Read )

MySQL 使用MVCC机制解决了不可重复读的问题,但是如果在开启事务后,执行了更新操作,还是会出现幻读问题

串行化( Serializable )

这个最好理解了,通过事务间进行排序,在每个读数据上加上共享锁,但是这个级别一般不用。

实战分析

读未提交

客户端A

代码语言:javascript
复制
set tx_isolation=' read-uncommitted '; 

start transaction;

客户端B

代码语言:javascript
复制
set tx_isolation=' read-uncommitted ';  
 
start transaction; 

客户端A

代码语言:javascript
复制
select * from test_tx;

客户端B

代码语言:javascript
复制
update test_tx set money=200 where id=3;

客户端A

代码语言:javascript
复制
select * from test_tx;

如果这时候A拿到b更新后的数据去做一些业务操作,当准备更新时,B回滚了事务

客户端B

代码语言:javascript
复制
rollback;

这时A拿到的就是脏数据,而且还有可能把脏数据更新到库里面了。

读已提交

客户端A

代码语言:javascript
复制
set tx_isolation=' read-committed ';  
start transaction;

客户端B

代码语言:javascript
复制
set tx_isolation=' read-committed ';  
start transaction;

客户端A

代码语言:javascript
复制
select * from test_tx;

客户端B

代码语言:javascript
复制
update test_tx set money=100 where id=3;
select * from test_tx;

客户端A

代码语言:javascript
复制
select * from test_tx;

可以看到读的数据没有变更

这时候B提交事务

客户端B

代码语言:javascript
复制
commit;

客户端A

代码语言:javascript
复制
select * from test_tx;

读到了已提交的变更,这就是不可重复度

可重复读

客户端A

代码语言:javascript
复制
set tx_isolation=' repeatable-read '; 
start transaction;

客户端B

代码语言:javascript
复制
set tx_isolation=' repeatable-read '; 
start transaction;

客户端A

代码语言:javascript
复制
select * from test_tx;

客户端B

代码语言:javascript
复制
update test_tx set money=50 where id=3;
commit;

客户端A

代码语言:javascript
复制
select * from test_tx;

A没有将B提交的数据查出来,解决了不可重复读的问题,难道说就没有问题了么

验证幻读

客户端A

代码语言:javascript
复制
set tx_isolation=' repeatable-read '; 
start transaction;

客户端B

代码语言:javascript
复制
set tx_isolation=' repeatable-read '; 
start transaction;

客户端A

代码语言:javascript
复制
select * from test_tx;

客户端B

代码语言:javascript
复制
insert into test_tx values(null,'乐哥聊编程',19);
commit;
select * from test_tx;

客户端A

代码语言:javascript
复制
select * from test_tx;

目前看来好像也没有什么问题,但是还是有问题的:客户端A

代码语言:javascript
复制
update test_tx set money=10 where id=4;
select * from test_tx;

神奇的发现b新增的数据被查出来了,这就是幻读了

串行化

代码语言:javascript
复制
set tx_isolation=' serializable '; 

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2022-11-05,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 乐哥聊编程 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 概念介绍
    • 读未提交( Read Uncommitted )
      • 读已提交( Read Committed )
        • 可重复读( Repeatable Read )
          • 串行化( Serializable )
          • 实战分析
            • 读未提交
              • 读已提交
                • 可重复读
                  • 验证幻读
                • 串行化
                相关产品与服务
                云数据库 MySQL
                腾讯云数据库 MySQL(TencentDB for MySQL)为用户提供安全可靠,性能卓越、易于维护的企业级云数据库服务。其具备6大企业级特性,包括企业级定制内核、企业级高可用、企业级高可靠、企业级安全、企业级扩展以及企业级智能运维。通过使用腾讯云数据库 MySQL,可实现分钟级别的数据库部署、弹性扩展以及全自动化的运维管理,不仅经济实惠,而且稳定可靠,易于运维。
                领券
                问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档