面试官:谈一谈你对MVCC的理解

100 阅读2分钟

一、事物的隔离级别

1.1 读未提交

会产生脏读不可重复读幻读

1.2 读已提交

会不可重复读,幻读

1.3 可重复读

会幻读

1.4 串行

都解决了,但是效率低

二、readview

创建readview的事物id最小事物id当前最大事物id+1活动事物id集合

三、MVCC是什么?

3.1 介绍

MVCC多版本并发控制,用来解决读取数据时不加锁来提高性能的一种方式,主要是通过readview和undolog日志实现的。我们之前提到过undolog日志是回滚日志,记录了每次insert update delete 执行之前的数据。

3.2 快照读 当前读

  • 快照读 select 语句
  • 当前读 加的是悲观锁
     SELECT * FROM student lock in share mode;
     SELECT * FROM student for update;
    

3.3 原理

  • 针对快照读,每次都是使用同一个readview,我们根据当前以及id以及readview判断是否数据针对当前事物可见,如果可见就是返回当前undolog的数据,否则顺着undolog的roll_pointer 一直往下找,直到找到可见的数据。
  • 针对当前读,加next-key-lock (记录锁和间隙锁)

3.4 怎么找可见?

刚开始我们的数据 余额 trx_id roll_pointer 100 10 10

图片.png

图片.png

  • A开启事务,更新数据余额为200,未提交事务

  • B开启事务,读取数据,余额200(此时undolog的trx_id为10,10比11小说明此条数据在事务B开启之前就提交了)

  • A commit,那么数据就变成了

    图片.png

    但是B还是用的之前那个readview,一看11还在活动事物列表中,就会往下找,发现10这个事物不在活动列表中,那么这条数据就是可见的

四、总结

MVCC是多版本并发控制,通过不加锁的方式提高数据的查询性能, 并且能够解决幻读的问题。主要是利用了readview和undolog日志的机制。通过判断当前事务id和readview中的事务字段以及undolog的版本链去找可见的数据。