当我们创建一个表之后,mysql会帮我们为这个表创建两个或三个隐藏字段,它们分别是
DB_TRX_ID:最近修改事务,记录插入这条记录或者最后一次修改该记录的事务ID,默认自增
DB_ROLL_PTR:回滚指针,指向这条记录的上一个版本,用于配合undo log,指向上一个版本
DB_ROW_ID:隐藏主键,如果表结构没有指定主键,将会生成隐藏主键,如果表里有主键,将不会生成这个隐藏字段
当我们创建一个表记录之后,表是这样的,db_trx_id默认从1开始,前面这是第一条数据,所以回滚指针指向的是null
假设现在有并发事务来操作这个记录
首先事务2要将id=30的记录的age修改为3,这个时候undo log日志就会记下未发生修改之前的数据
然后对记录进行更新操作,将age变为3,然后事务id变为事务2的id,回滚指针指向undo log中最近的那条记录的地址
这样如果这条记录出现问题,需要回滚,就会回滚到undo log中的那条记录
接下来事务3要将name修改为A3,这样的同样先是在undo log中记录未修改之前的数据
接着对记录进行修改
后面的同理,这块就不再多说了
来看看当执行完第四个事务时,会变成什么样
所以对于不同事务或相同事务对同一条记录进行修改,会导致该记录的undo log生成一条记录版本链,链表的头部是最新的记录,链表的尾部时最旧的记录。
但是当我们查询id=30的记录时,到底该返回哪个版本呢,这个是由readView决定的