当前位置: 首页 > article >正文

MySQL学习笔记(2)并发问题与事务隔离级别

本文参考:https://javaguide.cn/database/mysql/transaction-isolation-level.html

并发事务问题

脏读:一个事务读到了另一个事务中未提交的数据

在这里插入图片描述

不可重复读:一个事务先后读取同一条数据,当时两次获取到的结果不同

在这里插入图片描述

幻读:一个事务按照条件查询数据时,没有查到对应的数据行,当时在插入数据时,又发现这行数据已经存在

在这里插入图片描述

SQL中标准的四个隔离级别:

  • 读取未提交(READ-UNCOMMITTED):允许读取尚未提交的数据变更。
  • 读取已提交(READ-COMMITTED):允许读取并发事务已经提交的数据。
  • 可重复读(REPEATABLE-READ):对同一字段的多次读取结果都是一致的,除非数据是被本身事务自己所修改。
  • 可串行化(SERIALIZABLE):所有的事务依次逐个执行。
    在这里插入图片描述
    MySQL InnoDB 存储引擎的默认支持的隔离级别是 REPEATABLE-READ(可重读),但是通过MVCC 机制和 Next-Key Lock 机制防止了幻读现象的出现。

InnoDB 的 MVCC 机制

InnoDB 使用多版本并发控制(MVCC)来实现一致性读。MVCC 的核心思想是:

  • 每个事务都有一个唯一的事务 ID(事务版本号)。
  • 数据行会保存多个版本(通过隐藏的列 DB_TRX_ID 和 DB_ROLL_PTR 记录版本信息)。
  • 事务读取数据时,会根据自己的事务 ID 看到数据在事务开始时的快照版本,而不是实时版本。

MVCC 如何防止幻读?

  • 在 REPEATABLE-READ 级别下,事务 A 的快照版本是固定的,它只能看到在事务开始时已经存在的数据行。
  • 即使其他事务插入了新行,这些新行不会出现在事务 A 的快照版本中,因此事务 A 不会看到这些新行,从而避免了幻读。

Next-Key Lock 机制

InnoDB 在 REPEATABLE-READ 级别下使用 Next-Key Lock 来进一步防止幻读。Next-Key Lock 是行锁(Record Lock)和间隙锁(Gap Lock)的结合:

  • 行锁(Record Lock):锁定已存在的数据行。
  • 间隙锁(Gap Lock):锁定数据行之间的间隙,防止其他事务插入新行。

Next-Key Lock 如何防止幻读?

  • 当事务 A 对某个范围的数据进行读取时,InnoDB 会使用 Next-Key Lock 锁定整个范围(包括已存在的行和行之间的间隙)。
  • 如果事务 B 尝试在这个范围内插入新行,会被间隙锁阻塞,直到事务 A 提交或回滚。
    这样,事务 A 在整个事务期间都能保证范围内的数据不会被其他事务插入新行,从而防止了幻读。

不可重复读和幻读的区别是一个读取的一行,一个读取的是多行吗?

不可重复读和幻读的区别并不是由读取单行或多行决定的,而是由数据变化的类型决定的。以下是两者的详细区别:

1. 不可重复读(Non-Repeatable Read)

不可重复读是指在同一个事务中,两次读取同一行数据时,数据的内容发生了变化。这种现象通常是由于其他事务对该行数据进行了更新(UPDATE)操作。

特点:
  • 数据行不变:数据行的主键或唯一标识没有变化。
  • 数据内容变化:数据行的内容(字段值)发生了变化。
  • 解决方法:通过记录锁(Record Lock)锁定数据行,防止其他事务更新该行。

2. 幻读(Phantom Read)

幻读是指在同一个事务中,两次读取同一范围的数据时,数据的集合发生了变化。这种现象通常是由于其他事务在该范围内插入(INSERT)或删除(DELETE)了数据行。

特点:
  • 数据范围不变:查询的条件范围没有变化。
  • 数据集合变化:查询结果集中出现了新的行或某些行消失了。
  • 解决方法:通过间隙锁(Gap Lock)或 Next-Key Lock(记录锁 + 间隙锁)锁定数据范围,防止其他事务在该范围内插入或删除数据。

3. 不可重复读 vs. 幻读

  • 不可重复读:关注的是数据行的内容变化,通常是由于其他事务对同一行数据进行了更新操作。
  • 幻读:关注的是数据范围内的集合变化,通常是由于其他事务在范围内插入或删除了数据。

http://www.kler.cn/a/569954.html

相关文章:

  • kettle插件-git/svn版本管理插件
  • 实战 Elasticsearch:快速上手与深度实践-2.2.2线程池配置与写入限流
  • 乡村研学旅行小程序(论文源码调试讲解)
  • 【JavaScript】《JavaScript高级程序设计 (第4版) 》笔记-附录A-ES2018 和 ES2019
  • 芯麦GC1272与茂达APX9172驱动芯片技术对比及替代方案解析 ——以电脑散热风扇、工业风机及智能设备场景为例
  • Kaldi环境配置与Aishell训练
  • 解决:org.springframework.web.multipart.support.MissingServletRequestPartException
  • Windows下git疑难:有文件无法被跟踪
  • 【MySQL】窗口函数详解(概念+练习+实战)
  • 网络安全六层模型
  • 【R语言】加权回归拟合
  • 【决策树】分类属性的选择
  • 探秘Linux权限管理:数字背后的守望与秩序
  • Android Flow 示例
  • [JACCCI 2025]基于深度学习的舒张功能障碍风险模型对早期主动脉瓣狭窄进展的分层预测
  • 爬虫系列之【数据解析之JSON】《三》
  • 三维数据可视化与表面重建:Marching Cubes算法的原理与应用
  • 机器学习:强化学习的epsilon贪心算法
  • Android视频流畅播放要素
  • 视频生成FantasyID: Face Knowledge Enhanced ID-Preserving Video Generation