事务隔离级别

事务并发可能出现的问题

  • 脏写 事务之间对增删改互相影响
  • 脏读 事务之间读取其他未提交事务的数据
  • 不可重复读 一个事务在多次执行一个select读到的数据前后不相同。因为被别的未提交事务修改,删除数据或数据被更新被当前事务读取到了。
  • 幻读 一个事务在第一次读取正常数据,第二次读取到其他未提交事务的insert记录,导致读取一个不存在的记录。指一次读取读取到了之前未读取到的数据。

事务的4个隔离级别,以及解决的问题

  • READ UNCOMMITTED 未提交读 解决脏写
  • READ COMMITTED提交读 解决脏写、脏读
  • REPEATABLE READ可重复读 解决脏写、脏读、不可重复读
  • SERIALIAZBLE可串行化 解决脏写、脏读、不可重复读、幻读

四个隔离级别和可以解决的问题是SQL专门规定的,但是在Innodb引擎下,在可重复读的隔离级别的下就可以直接解决幻读的问题。

我们可以在启动时指定系统参数修改系统默认的隔离级别,默认为可重复读。

mysql> show variables like 'transaction_isolation';
+-----------------------+-----------------+
| Variable_name | Value |
+-----------------------+-----------------+
| transaction_isolation | REPEATABLE-READ |
+-----------------------+-----------------+
1 row in set, 1 warning (0.00 sec)

MVCC

版本链

我们在前面就讲过了undo日志,对于每次进行增删改就会产生undo日志,这时每个数据行的roll_pointer就会指向一个undo链表,我们就称其为版本链。我们在提一嘴,因为insert的undo日志在提交后是没有用的,所以在事务提交后insert的undo就会被释放。

可以到前面的文章了解一下undo日志。大概知道undo日志的类型和产生的过程就OK了感觉怎么存储undo日志的那一部分讲得云里雾里https://www.cnblogs.com/duizhangz/p/16333565.html

为什么没用?因为插入并不维护旧值,只是表明一个插入,并不需要存储什么信息。所以在事务提交时直接释放掉。因为事务在回滚时需要由一条insert语句类型的undo进行回滚。

这就是上面俩事务生成的版本链。

undo链表头存储的就是最新事务更新的记录信息。

ReadView

对于不同的事务隔离级别,我们可以读取的记录数据是不一样的。

  • 对于未提交读的隔离级别来说,我们可以直接读到数据的最新版本。

  • 对于提交读的隔离级别来说,我们需要可以读到的就是已经提交的事务的修改数据。

  • 对于可重复读的隔离级别来说,我们需要可以读到在事务开启前已经提交的事务的数据。

  • 对于串行读的隔离节别来说,Innodb采用加锁的方式来保证串行读。

对于中间两个隔离级别,就需要ReadView这个结构来实现MVCC。以下是ReadView的结构

  • m_ids : 表示在生成ReadView时当前系统中活跃的读写事务ID的列表
  • min_trx_id : 表示在生成ReadView时当前系统中活跃的读写事务ID的最小值即在m_ids中最小的事务ID。
  • max_trx_id : 表示生成ReadView时系统中应该分配给下一个事务的ID。
  • creator_trx_id : 表示生成该ReadView的事务ID。

有了ReadView这个结构,我们在就可以对事务进行控制。

  • 当被访问的记录行的事务ID大于等于max_trx_id,说明当前数据行不可见。
  • 当被访问的记录行的事务ID小于min_trx_id,可以直接获得数据。
  • 当被访问的记录行的事务ID等于creator_trx_id,说明是当前事务修改的记录,可以直接访问。
  • 当被访问的记录行的事务ID大于min_trx_id且小于max_trx_id,我们需要判断一下这个事务ID是不是在m_ids列表中,因为由可能是一个很早的事务很久还执行不介绍,导致中间的事务都结束了,如果在m_ids列表中,说明是活跃的,当前记录行不能访问,否则可以访问数据行。

当前情况在版本链中从头到尾遍历,直到获得到数据。

上面提到的提交读和可重复读,因为是两个隔离级别有区别的,两个隔离级别的实现只要在ReadView的时机上进行把控,就可以实现。

  • 提交读,我们只要保证当前事务的每个语句能读到已经提交的事务的数据。就可以在每个查询数据进行前,事务就会创建一个ReadView。
  • 可重复读,我们只要保证当前事务每个语句能读到事务开启前的数据,就可以在事务第一次读取数据时会创建ReadView,然后整个事务只会使用这个ReadView去判断能读取的数据行。

仔细品一品,一下就可以恍然大悟。

这个MVCC只会在我们使用普通select查询才会生效。

MySQL之事务隔离级别和MVCC的更多相关文章

  1. 一文读懂MySQL的事务隔离级别及MVCC机制

    回顾前文: 一文学会MySQL的explain工具 一文读懂MySQL的索引结构及查询优化 (同时再次强调,这几篇关于MySQL的探究都是基于5.7版本,相关总结与结论不一定适用于其他版本) 就软件开 ...

  2. 【mysql】- 事务隔离级别和MVCC篇

    概念 术语 脏写( Dirty Write ): 如果一个事务修改了另一个未提交事务修改过的数据,那就意味着发了脏写 脏读( Dirty Read ) : 如果一个事务读到了另一个未提交事务修改过的数 ...

  3. MySQL实战 | 03 - 谁动了我的数据:浅析MySQL的事务隔离级别

    原文链接:这一次,带你搞清楚MySQL的事务隔离级别! 使用过关系型数据库的,应该都事务的概念有所了解,知道事务有 ACID 四个基本属性:原子性(Atomicity).一致性(Consistency ...

  4. 【MySQL】事务隔离级别及ACID

    注:begin或start transaction并不是一个事务的起点,而是在执行它们之后的第一个操作InnoDB表的语句,事务才真正开始.start transaction with consist ...

  5. MySQL之事务隔离级别--转载

    转自:http://793404905.blog.51cto.com/6179428/1615550 本文通过实例展示MySQL事务的四种隔离级别. 1 概念阐述 1)Read Uncommitted ...

  6. 重新学习MySQL数据库8:MySQL的事务隔离级别实战

    重新学习Mysql数据库8:MySQL的事务隔离级别实战 在Mysql中,事务主要有四种隔离级别,今天我们主要是通过示例来比较下,四种隔离级别实际在应用中,会出现什么样的对应现象. Read unco ...

  7. mysql数据库——事务隔离级别

    四种隔离级别: 一:READ UNCOMMITTED(未提交读) 事务可以读取其他事务未提交的数据,称为脏读 二:READ COMMITTED(提交读) 一个事务开始时,只能"看见" ...

  8. 【Java面试】请你简单说一下Mysql的事务隔离级别

    一个工作了6年的粉丝,去阿里面试,在第一面的时候被问到"Mysql的事务隔离级别". 他竟然没有回答上来,一直在私信向我诉苦. 我说,你只能怪年轻时候的你,那个时候不够努力导致现在 ...

  9. Mysql数据库事务隔离级别

    事务(transaction)是数据库管理系统的执行单位,可以是一个数据库操作(如Select操作)或者是一组操作序列.事务ACID属性,即原子性(Atomicity).一致性(Consistency ...

随机推荐

  1. 浅谈ES6中的Class

    转载地址:https://www.cnblogs.com/sghy/p/8005857.html 一.定义类(ES6的类,完全可以看做是构造函数的另一种写法) class Greet { constr ...

  2. vux+vue-cli3.0坑

    最近开发了项目使用了vue-cli3.0+vux搭建的项目,现在总结遇到的问题: 环境:github vux有关于vue-cli3.0以及vux已经搭建好的脚手架vux-cli3链接 一:如下报错 解 ...

  3. python数据类型与基础运算

    注释:了解其他数据类型补充 基础数据类型补充 可以回一下之前的数据类型: 整型,浮点型,字串符和列表. 一.字典(dict) #字典:可以精准的储存数据 是用大括号表示'{}' '字典和数据数据列表差 ...

  4. mybatis在if标签里判断字符串相等

    https://www.cnblogs.com/westward/p/6910856.html

  5. vue3响应式模式设计原理

    vue3响应式模式设计原理 为什么要关系vue3的设计原理?了解vue3构建原理,将有助于开发者更快速上手Vue3:同时可以提高Vue调试技能,可以快速定位错误 1.vue3对比vue2 vue2的原 ...

  6. Python 一网打尽<排序算法>之先从玩转冒泡排序开始

    1. 前言 所谓排序,就是把一个数据群体按个体数据的特征按从大到小或从小到大的顺序存放. 排序在应用开发中很常见,如对商品按价格.人气.购买数量--显示. 初学编程者,刚开始接触的第一个稍微有点难理解 ...

  7. 谈谈.NET Core下如何利用 AsyncLocal 实现共享变量

    前言 在Web 应用程序中,我们经常会遇到这样的场景,如用户信息,租户信息本次的请求过程中都是固定的,我们希望是这种信息在本次请求内,一次赋值,到处使用.本文就来探讨一下,如何在.NET Core 下 ...

  8. node.js - 路由、中间件、mysql

    这几天天天搞到这么晚,我看今天的内容看起不多啊,不知道为什么学着学着就到了这么晚.今天的内容还是有点多哈,有点自我矛盾了,再次一一道来. 1. 首先今天先看到路由的概念,什么叫做路由? 路由就是映射关 ...

  9. python基础练习题(题目 有序列表插入元素)

    day26 --------------------------------------------------------------- 实例039:有序列表插入元素 题目 有一个已经排好序的数组. ...

  10. k8s面试1-27

    目录 1.k8s常用命令有哪些? 2.报错查看各种日志方法? 3.k8s的组建有哪些? 4.k8s中安全机制是什么? 5.常用的控制器有哪些? 6.service类型有哪些? 7.ingress-Ng ...