MySQL事务隔离级别之理解篇

本文涉及的产品
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
RDS MySQL Serverless 高可用系列,价值2615元额度,1个月
简介: 说到MySQL事务,大家更多就是知道增删改查。以及事务就是开启事务,提交或者回滚事务,其他的一概模糊,可能大家更多的是停留在应用层面。说到MySQL的事务隔离级别,小马特意翻阅了一些网上教程,诸如菜鸟教程,发现并无相关的介绍。还是整理一下吧,毕竟一般也是面试时候的必考题。

说到MySQL事务,大家更多就是知道增删改查。以及事务就是开启事务,提交或者回滚事务,其他的一概模糊,可能大家更多的是停留在应用层面。说到MySQL的事务隔离级别,小马特意翻阅了一些网上教程,诸如菜鸟教程,发现并无相关的介绍。还是整理一下吧,毕竟一般也是面试时候的必考题。

什么是事务

什么是事务?小马曾经就有被问到这样的问题。

1、在 MySQL 中只有使用了 Innodb 数据库引擎的数据库或表才支持事务。

2、事务处理可以用来维护数据库的完整性,保证成批的 SQL 语句要么全部执行,要么全部不执行。

3、事务用来管理 insert,update,delete 语句。

一般来说,事务是必须满足4个条件(ACID)::原子性(Atomicity,或称不可分割性)、一致性(Consistency)、隔离性(Isolation,又称独立性)、持久性(Durability)。

原子性:一个事务(transaction)中的所有操作,要么全部完成,要么全部不完成,不会结束在中间某个环节。事务在执行过程中发生错误,会被回滚(Rollback)到事务开始前的状态,就像这个事务从来没有执行过一样。

一致性:在事务开始之前和事务结束以后,数据库的完整性没有被破坏。这表示写入的资料必须完全符合所有的预设规则,这包含资料的精确度、串联性以及后续数据库可以自发性地完成预定的工作。

隔离性:数据库允许多个并发事务同时对其数据进行读写和修改的能力,隔离性可以防止多个事务并发执行时由于交叉执行而导致数据的不一致。事务隔离分为不同级别,包括读未提交(Read uncommitted)、读提交(read committed)、可重复读(repeatable read)和串行化(Serializable)。

持久性:事务处理结束后,对数据的修改就是永久的,即便系统故障也不会丢失。

彩蛋来了,一般情况下我们对MySQL执行比如update和insert,delete语句,但是直接执行完就可以了,那么你可知道这里其实MySQL有一步自动commit的操作,像开启事务一样的,只不过这里是隐式的提交,这个是否自动提交的值其实是可以设置的。也就是如果你把它设置为非自动提交,那么像你平时执行完update后还要执行commit。教程是这么说的:

在 MySQL 命令行的默认设置下,事务都是自动提交的,即执行 SQL 语句后就会马上执行 COMMIT 操作。因此要显式地开启一个事务务须使用命令 BEGIN 或 START TRANSACTION,或者执行命令 SET AUTOCOMMIT=0,用来禁止使用当前会话的自动提交。

MySQL事务隔离级别

谈到事务的ACID四个条件之一隔离性,什么是隔离性,可以通俗理解为两个事务之间互相互不干扰。其实它也是有级别的,那就是事务隔离级别。注意,敲黑板,这是考点。

事务的隔离级别有四个:未提交读(read uncommitted)、已提交读(read committed)、可重复读(repeatable read)、串行化(serializable)。也可以记为读未提交、读已提交、可重复读、串行化,更好理解和记忆。

未提交读:A事务已执行,但未提交;B事务查询到A事务的更新后数据;A事务回滚;也就是B读到了A的未提交数据,然后A最后还不提交直接回滚了,导致B最后取到的数据为脏数据,也叫作脏读。

已提交读:A事务执行更新;B事务查询;A事务又执行更新;B事务再次查询时,前后两次数据不一致;也就是B读到了A未提交期间的数据,然后A改了数据,B又去读数据,最后A提交了修改,B又去读了数据。导致B多次获取到的数据和最后A提交的数据都是不同的,这个也叫不可重复读。

可重复读:A事务无论执行多少次,只要不提交,B事务查询值都不变;B事务仅查询B事务开始时那一瞬间的数据快照;也就是只要A事务还没提交,B每次读,都是B事务开始时的快照数据。类似于改操作时对相应的数据行加了行级锁。但试想一个问题,假设你在更改数据,读出1000条数据,要把性别字段由原来的A代表男B代表女改为1代表男2代表女,在你开启B事务执行期间,A事务对表新增一条数据,还是用A代表男的数值。那么最后你提交完B事务,还是会存在一条未修改过来的数据。这也叫做幻读。

串行化:不允许读写并发操作,写执行时,读必须等待,读写数据都会锁住整个索引范围的数据,可以理解为类似锁表;这样就不会幻读了,但是对并发的支持不友好。

MYSQL默认的事务隔离级别为可重复读(repeatable read)。隔离级别越高,越能保证数据的完整性和一致性,但是对并发性能的影响也越大。借用一张图便于记忆。
image.png

各级别考可能导致的问题


Redis事务就没有隔离级别的概念,批量操作在发送EXEC命令前被放入队列缓存,并不会被实际执行(本身事务执行就不会互相干扰),也就是在事务提交之前不会被实际执行,也就不存在“事务内的查询要看到事务里的更新,事务外查询不能看到”这个头疼的问题。也就是它是提交后命令打包执行的,不存在事务中更新了一半未提交被别人读取值的情况。

mvcc在事务隔离级别中的作用

仅InnoDB支持mvcc。应对高并发事务, MVCC比单纯的加锁更高效;MVCC只在READ COMMITTED和REPEATABLE READ两个隔离级别下工作;MVCC可以使用乐观(optimistic)锁和悲观(pessimistic)锁来实现;各数据库中MVCC实现并不统一。

MySQL大部分的事务型存储引擎都不是简单的行级锁,基于提升性能的角度考虑,一般都会实现多版本并发控制(mvcc)。

mvcc的实现,是根据数据在某个时间点的快照来实现的,也就是说,一个事务,不管执行多长时间,该事务从头到尾看到的数据都是一致的。根据事务的开始时间不同,每个事务在同一时刻看到的数据可能是不一致的。

InnoDB的MVCC,是通过在每行后面加两个隐藏列来实现的(分别保存行的创建时间和过期时间),当然里面存的并不是真正意义的时间,而是系统版本号。每开始一个新的事务,系统版本号都会递增,事务开始时间的版本号会作为当前事务的版本号。

相关实践学习
基于CentOS快速搭建LAMP环境
本教程介绍如何搭建LAMP环境,其中LAMP分别代表Linux、Apache、MySQL和PHP。
全面了解阿里云能为你做什么
阿里云在全球各地部署高效节能的绿色数据中心,利用清洁计算为万物互联的新世界提供源源不断的能源动力,目前开服的区域包括中国(华北、华东、华南、香港)、新加坡、美国(美东、美西)、欧洲、中东、澳大利亚、日本。目前阿里云的产品涵盖弹性计算、数据库、存储与CDN、分析与搜索、云通信、网络、管理与监控、应用服务、互联网中间件、移动服务、视频服务等。通过本课程,来了解阿里云能够为你的业务带来哪些帮助     相关的阿里云产品:云服务器ECS 云服务器 ECS(Elastic Compute Service)是一种弹性可伸缩的计算服务,助您降低 IT 成本,提升运维效率,使您更专注于核心业务创新。产品详情: https://www.aliyun.com/product/ecs
相关文章
|
1月前
|
SQL 关系型数据库 MySQL
轻松入门MySQL:保障数据完整性,MySQL事务在进销存管理系统中的应用(12)
轻松入门MySQL:保障数据完整性,MySQL事务在进销存管理系统中的应用(12)
|
1月前
|
SQL 安全 关系型数据库
【MySQL实战笔记】03.事务隔离:为什么你改了我还看不见?-01
【4月更文挑战第6天】MySQL事务的隔离性确保数据操作的完整性和一致性,ACID原则包括原子性、一致性、隔离性和持久性。事务隔离级别有四种:读未提交、读提交、可重复读和串行化,分别解决并发问题如脏读、不可重复读和幻读。不同隔离级别在效率和安全性间权衡,例如读未提交允许未提交变更可见,而串行化通过锁保证安全但可能降低效率。在不同隔离级别下,事务看到的数据状态会有所变化,例如在可重复读级别,事务始终看到初始数据,而在串行化级别,事务会等待其他事务完成再继续,避免数据冲突。
278 10
|
4天前
|
SQL 存储 关系型数据库
MySQL索引及事务
MySQL索引及事务
15 2
|
4天前
|
存储 算法 关系型数据库
MySQL事务与锁,看这一篇就够了!
MySQL事务与锁,看这一篇就够了!
|
5天前
|
Java 关系型数据库 MySQL
MySQL 索引事务
MySQL 索引事务
13 0
|
12天前
|
SQL 安全 关系型数据库
【Mysql-12】一文解读【事务】-【基本操作/四大特性/并发事务问题/事务隔离级别】
【Mysql-12】一文解读【事务】-【基本操作/四大特性/并发事务问题/事务隔离级别】
|
14天前
|
存储 关系型数据库 MySQL
Mysql学习--深入探究索引和事务的重点要点与考点
Mysql学习--深入探究索引和事务的重点要点与考点
|
15天前
|
存储 SQL 关系型数据库
Mysql_数据库事务
Mysql_数据库事务
|
16天前
|
缓存 关系型数据库 MySQL
【专栏】提升MySQL性能和高可用性的策略,包括索引优化、查询优化和事务管理
【4月更文挑战第27天】本文探讨了提升MySQL性能和高可用性的策略,包括索引优化、查询优化和事务管理。通过合理使用B-Tree和哈希索引,避免过度索引,以及优化查询语句和利用查询缓存,可以改善性能。事务管理中,应减小事务大小并及时提交,以保持系统效率。主从或双主复制可增强高可用性。综合运用这些方法,并根据实际需求调整,是优化MySQL的关键。
|
17天前
|
Java 关系型数据库 MySQL
{MySQL}索引事务和JDBC
{MySQL}索引事务和JDBC
21 0