目录
三、已提交读和可重复读的底层实现 MVCC(多版本并发控制)
一、事务隔离级别的实现原理 锁 + MVCC
1.1、怎么引出锁呢?
1.2、表级锁&行级锁
1.3、排它锁和共享锁
普通字段为过滤条件:
所以我们能得出结论:Innodb的行锁是加在索引上面的,是给索引在加锁,并不是给单纯的行记录在加锁;所以如果过滤条件没用加索引的话,使用的就是表锁,而不是行锁
二、串行化怎么解决幻读问题的呢? 间隙锁
2.1、范围查询条件下
间隙锁(gap lock)
但是我们这时候能插入吗?不能
为什么insert不了呢?就是因为间隙锁的存在
间隙锁给查询范围的间隙之间都加上了锁
2.2、等值查询条件下
当用主键为过滤条件的时候,是不用管的,因为主键不能重复,就算再次插入相同的数据,也是直接就会失败的
但是普通索引(辅助索引)的话就有问题要探讨了
三、已提交读和可重复读的底层实现 MVCC(多版本并发控制)
MVCC(多版本并发控制)==》并发的读取方式:快照读
innodb提供两个读取操作: 锁定读 和 非锁定读 MVCC提供的快照读 =》依赖底层的一个技术 =》undo log回滚日志
3.1、undo log回滚日志的主要作用
1、事务发生错误时回滚rollback
2、提供了MVCC的非锁定读(快照读) 得从undo log的原理说起
3.2、已提交读是怎么解决脏读的呢?
我们都知道,已提交读的隔离级别下,能够解决“脏读”,但不能解决不可重复读
已提交读用的读是非锁定读,就是不是通过加锁来实现的,而是用到了MVCC提供的快照读
3.2、已提交读 为什么会有 不可重复读 和 幻读?
因为其他事务更新后而且已提交的数据(commit过了),可以实时反馈到当前事务的select快照中!
每一次select都会重新产生一次数据快照。
幻读的产生就和这个相似了:
因为每一次select都会产生一次数据快照,其他食物增加了和当前事务查询条件相同的新的数据,并且已成功commit提交,导致当前事务再次以相同的条件查询时,数据多了
3.3、可重复读 为什么解决了 不可重复读问题?
第一次select产生了数据快照,而且只产生一次。
3.3、可重复读 为什么部分解决了 幻读问题?
解决了insert导致的幻读问题:
当前事务是可以看到自己事务的修改、更新的操作
当前事务用了update,还是会出现幻读的现象,并没用完全规避掉。
四、意向共享锁与意向排他锁
这两个锁都是和表锁相关的,目的是为了更快的获取表锁
使用表锁的时候,涉及一个效率的问题?
五、死锁问题
实际使用MySQL时: