首页 > 数据库 >MySQL 事务和MVCC原理

MySQL 事务和MVCC原理

时间:2023-02-11 14:55:32浏览次数:43  
标签:事务 log read MVCC undo 版本 MySQL view

       事务定义

   事务是一组操作,这些操作可以是一条SQL语句、一组SQL语句或整个程序。

           什么时候会用到事务呢?当多张强一致关联的表,需要进行数据同步的时候,就需要开启事务

 

  事务特性

  •  原子性 (atomicity): 强调事务的不可分割.最小执行逻辑单位。事务只会全部成功或全部失败。
  •  一致性 (consistency): 事务的执行的前后数据的完整性保持一致。这是基于原子性做到的。
  •  隔离性 (isolation): 一个事务执行的过程中,不应该受到其他事务的干扰。
  •  持久性(durability) : 事务一旦结束,数据就持久到数据库。

 

  事务隔离级别

   

  

      建议的隔离级别

    建议使用读已提交(RC)。从性能上考虑:

  •     RR比RC多使用间隙锁,死锁概率高 (RR会使用记录锁和间隙锁。间隙锁:锁定一个范围,不包含记录本身,防止其他事务增删造成二次查询的数据有差异,解决不可重复读问题)
  •     使用不了索引会锁表

      从逻辑上说,每次读到最新提交的数据,也符合正常思维。

 

    MVCC原理

     MVCC(Multiversion concurrency control) 就是同一份数据保留多版本的一种方式,进而实现并发控制(事务并发)通过undo log版本链和read view实现

 

         undo log 版本链

          MVCC 的实现依赖于版本链,版本链是通过表的三个隐藏字段实现。

  • DB_TRX_ID:当前事务id,通过事务id的大小判断事务的时间顺序。
  • DB_ROLL_PTR:回滚指针,指向当前行记录的上一个版本,通过这个指针将数据的多个版本连接在一起构成undo log版本链。
  • DB_ROW_ID:主键,如果数据表没有主键,InnoDB会自动生成主键。    

         新增一条表记录大概是这样的:

         insert into test (name,age) values (duiker,12);

       

        当事务更新该记录的时候,会生成undo log。执行过程如下:

  1.排它锁锁住行

       2.复制一份数据到undo log。

       3.修改当前行的值。生成一个新版本,回滚指针指向该条undo log的地址。

  执行结果如下:

  update test set name = duikerdd where name = duiker;

       

       4.此时undo log有一条数据。

 

        read view 快照

          read view可以理解成将数据在每个时刻的状态拍成“照片”记录下来。在获取某时刻t的数据时,到t时间点拍的“照片”上取数据。

   在read view内部维护一个活跃事务链表,表示快照的活跃事务。这个链表包含在创建read view之前还未提交的事务,不包含创建read view之后提交的事务。
不同隔离级别,read view生成时机也不同:
  •    RC:每次执行select都会创建新的read_view,保证能读取到其他事务已经提交的修改。
  • RR:在一个事务范围内,第一次select时更新这个read_view,以后不会再更新,后续所有的select都是复用之前的read_view。这样可以保证事务范围内每次读取的内容都一样,即可重复读。
         read view的记录筛选方式
   前提:DATA_TRX_ID 表示每个数据行的最新的事务ID;up_limit_id表示当前快照中的最先开始的事务;low_limit_id表示当前快照中的最慢开始的事务,即最后一个事务。
  •    如果DATA_TRX_ID < up_limit_id:说明在创建read view时,修改该数据行的事务已提交,该版本的记录可被当前事务读取到。  
  •      如果DATA_TRX_ID >= low_limit_id:说明当前版本的记录的事务是在创建read view之后生成的,该版本的数据行不可以被当前事务访问。此时需要通过版本链找到上一个版本,然后重新判断该版本的记录对当前事务的可见性。
  •      如果up_limit_id <= DATA_TRX_ID < low_limit_i:需要在活跃事务链表中查找是否存在ID为DATA_TRX_ID的值的事务。如果存在,因为在活跃事务链表中的事务是未提交的,所以该记录是不可见的。此时需要通过版本链找到上一个版本,然后重新判断该版本的可见性。如果不存在,说明事务trx_id 已经提交了,这行记录是可见的。

  总结:InnoDB 的MVCC是通过 read view 和undo log版本链实现的,版本链保存有历史版本记录,通过read view 判断当前版本的数据是否可见,如果不可见,再从版本链中找到上一个版本,继续进行判断,直到找到一个可见的版本。

  这样在多个事务中,可以同时读到相应的可见数据。 从而实现了事务并发控制。

 

标签:事务,log,read,MVCC,undo,版本,MySQL,view
From: https://www.cnblogs.com/Duikerdd/p/17110924.html

相关文章

  • 网易一面:select分页要调优100倍,说说你的思路?(内含Mysql的36军规)
    文章很长,而且持续更新,建议收藏起来,慢慢读!疯狂创客圈总目录博客园版为您奉上珍贵的学习资源:免费赠送:《尼恩Java面试宝典》持续更新+史上最全+面试必备2000页+面......
  • RPM 安装 Mysql8.0
    一、环境Centos Stream8 ---Linuxversion4.18.0-326.el8.x86_64([email protected])(gccversion8.5.020210514(RedHat8.5.0-3)(GCC))......
  • mysql为何使用B+树作为索引
    讲mysqlinnodb使用B+树作为索引的原因:https://juejin.cn/post/7081065180301361183分析mysql数据特点:存储在磁盘,为了提升性能,需要尽量减少io操作分析所有数据结构:线性......
  • mysql-proxy 读写分离,不支持mysql5.7的client客户端登录
    安装前,先有mysql主从下载proxy,https://downloads.mysql.com/archives/proxy/#downloadswgethttps://downloads.mysql.com/archives/get/p/21/file/mysql-proxy-0.8.5-......
  • 饱和度 - 监控MySQL的InnoDB Buffer pool 相关的指标
    1. 对于MySQL而言,用什么指标来反映资源有多“满”呢?首先我们要关注MySQL所在机器的CPU、内存、硬盘I/O、网络流量这些基础指标2. MySQL本身也有一些指标来反映饱......
  • linux安装 mysql
    在终端中输入命令安装mysqlsudoapt-getinstallmysql-server安装成功后可以在终端中输入下面命令登录mysql不知道为什么,在网上搜索有的会说安装的时候会让你设置......
  • MySQL数据类型
    数值类型关键字INT是INTEGER的同义词,关键字DEC是DECIMAL的同义词。TINYINT1Bytes(-128,127)(0,255)小整数值SMALLINT2Bytes(-32768,32767)(0,65535)大整......
  • MySQL数据库系统部署使用
    推荐步骤:在centos01上安装MySQL数据库服务,生成服务器配置文件,添加系统服务优化命令初始化MySQL,设置访问密码登录MySQL数据库 在centos01的MySQL服务器上创建数据库,数据库......
  • 性能分析 | MySQL Index Condition Pushdown(ICP)
    介绍概念介绍索引下推(IndexConditionPushdown,简称ICP),是MySQL5.6版本的新特性,ICP是针对MySQL使用索引从表中检索行的情况的优化方式关闭ICP,存储引擎会遍历索引以定位......
  • MySQL数据库系统部署使用
    拓扑图:推荐步骤: 在centos01上安装MySQL数据库服务,生成服务器配置文件,添加系统服务优化命令初始化MySQL,设置访问密码登录MySQL数据库 在centos01的MySQL服务器上创建数据......