Mysql-Innodb引擎MVCC实现原理

InnoDB MVCC实现原理

什么是可重复读?

  • 可重复读是指在一个事务中重复执行一个相同范围的查询,看到的结果是一样的;

什么是幻读?

  • 在可重复读的基础上,执行两次相同的范围查询,在第一次和第二次之间 有另一个事务插入了一个数据。导致第二次和第一次看到的数据不一样。

数据库隔离级别

  1. 读未提交
  • 脏读 不可重复读 幻读
  1. 读已提交
  • 不可重复读 幻读
  1. 可重复读
  • 基于快照读,在当前读模式下还是无法解决幻读(mysql默认隔离级别)innodb 使用mvcc解决幻读问题
  1. 串行化
  • 避免脏读、不可重复读和幻读的问题 使用加锁读

InnoDB如何解决幻读?

  1. 使用MVCC(多版本并发控制)机制
  2. MVCC实现原理
    1. InnoDB在行级别上使用共享锁和排他锁。每行数据实际上包含隐藏的版本信息。包括行的创建版本号和过期版本号。
    2. 版本号是递增的事务ID,由InnoDB自动分配。当一个事务开始时,它会获得一个事务ID,这个ID就是事务可见性依据。
  3. 读取视图
    1. 读取操作会创建一个读取视图,这个视图决定了哪些行版本对当前事务可见。
    2. 读取视图基于事务ID来过虑行版本,只有在事务开始之前提交的行版本才对当前事务可见。
    3. InnoDB使用最小未见事务ID和最大事务ID来快速确定行版本是否可见。
  4. 插入行
    1. 当事务插入新行事,InnoDB会为新行分配一个版本号(事务ID)并将其设置为当前事务ID
    2. 新行版本号就是其创建版本号,没有过期版本号。对后续事务都是可见,直到做了更新和删除事务。
  5. 删除标记
    1. 删除不是物理删除,设置一个删除标记。并创建一个删除版本。这个版本相当于当前事务ID
    2. 所有事务ID小于或等于删除版本的事务将看到该行,而更高的事务ID将看不到该行,就像它已被删除一样。
  6. 间隙锁和Next-Key锁
    1. 为了防止幻读,InnoDB使用间隙锁(Gap Locks)和Next-Key锁(Next-Key Locks)来锁定行之间的间隔。
    2. Next-Key锁是行锁和间隙锁的组合,确保了事务隔离级别下的完整性。

疑问

  1. 当两个相同事务同时更新一行。看到的是都被更新成功?背后执行原理?

    顺序执行 并非并发执行

    • 当一个事务执行更新,获取排他锁,其他任务事务都无法获取这行数据上任何类型锁无论共享还是排他锁。

    锁释放时机

    • 当事务被提交或者回滚

    事务可见性

    • 基于事务可见性特性 第二个事务执行前是可以看到第一个事务的更新操作,然后基于第一个事务上做的更新。

    锁释放默认超时时间

    • 默认是50秒 可以使用 SHOW VARIABLES LIKE 'innodb_lock_wait_timeout'; 进行查询
posted @ 2024-07-18 14:03  贺艳峰  阅读(31)  评论(1编辑  收藏  举报