MVCC(Multi Version Concurrency Control)多版本并发控制
InnoDB通过MVCC来实现事务的隔离性,控制事务的并发。
MVCC通过版本链实现多版本,可并发读-写、写-读。ReadView的不同生成策略来实现隔离级别。
事务对记录的修改会保存在版本链中,多个事务修改后,就有多个版本。在(Read Commited)读已提交、Repeatable Read可重复读隔离级别下,其他事务的Select操作可以访问记录的版本链,因此可以并发读-写、写-读。
版本链
在InnoDB的引擎表中,聚簇索引记录有两个隐藏列,txid、roll_pointer,txid保存上一次修改记录的事务id,roll_pointer指向上一个版本。
对聚簇索引记录修改后,会将老版本写到undo segment回滚段中。通过roll_pointer可以找到上一个版本。
ReadView
每个事务都有ReadView。ReadView包含了当前事务id、所有活跃事务的id、最小活跃事务id、最大活跃事务id。某个事务执行Select操作访问记录的版本链,从链头开始找到一个能访问就返回。
能访问的判断
- 记录上的事务id等于当前事务id,说明这个记录是当前事务自己修改的,可访问
- 记录上的事务id小于ReadView中事务的最小id,说明事务已经提交,可访问。
- 记录上的事务id大于ReadView中事务的最大id,说明记录在ReadView生成之后被修改了,不可访问
- 介于最大和最小之间,若事务id在ReadView中,说明事务未提交,不可访问,不在ReadView说明已提交可访问。
Read Commited读已提交隔离级别,每次Select都会重新生成ReadView,这样未提交的记录版本就不会被访问。
Repeatable Read可重复读隔离级别,第一次Select后生成ReadView,之后不生成。