1. 事务隔离级别基础回顾
在数据库系统中,事务隔离级别是保证数据一致性的核心机制之一。SQL标准定义了四种隔离级别,其中可重复读(Repeatable Read, RR)是许多数据库系统的默认选择。我们先来理解几个关键概念:
- 脏读:一个事务读取了另一个未提交事务修改的数据
- 不可重复读:同一事务内多次读取同一数据,结果不同(被其他事务修改)
- 幻读:同一事务内执行相同查询,返回的行数不同(其他事务新增/删除了数据)
可重复读隔离级别的主要承诺是:在一个事务内,多次读取同一数据会得到相同结果。这通过多版本并发控制(MVCC)实现,每个事务看到的是特定时间点的数据快照。
注意:不同数据库对RR的实现有差异。Oracle的RR实际实现了串行化,而MySQL的InnoDB在RR下仍可能出现幻读。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. InnoDB中RR隔离的实现机制
2.1 MVCC与ReadView
InnoDB通过以下机制实现RR隔离:
-
每行记录包含隐藏字段:
- DB_TRX_ID:最后修改该行的事务ID
- DB_ROLL_PTR:回滚指针,指向undo日志
- DB_ROW_ID:行ID
-
ReadView结构包含:
- m_ids:活跃事务ID列表
- min_trx_id:最小活跃事务ID
- max_trx_id:预分配的下个事务ID
- creator_trx_id:创建该ReadView的事务ID
事务首次读取时创建ReadView,后续读取复用同一视图,保证"可重复读"。
2.2 快照读与当前读
- 快照读:普通SELECT语句,读取历史版本
- 当前读:特殊读取方式,获取最新提交数据
sql复制SELECT ... FOR UPDATE SELECT ... LOCK IN SHARE MODE INSERT/UPDATE/DELETE操作前的读取
3. RR隔离级别的主要缺陷
3.1 幻读问题
虽然RR防止了不可重复读,但在InnoDB中仍可能出现幻读。考虑以下场景:
sql复制-- 事务1
START TRANSACTION;
SELECT * FROM users
