经典面试题:什么是事物的隔离级别?什么是MVCC?

目录

    • 前言
    • 一、事物的隔离级别
    • 二、隔离级别是如何实现的
      • 1. 锁定技术
      • 2. 多版本并发控制(MVCC)
        • 基本原理
        • 实现机制
        • 优缺点
      • 3. 乐观锁与悲观锁
    • 三、MySQL设置隔离级别
      • MySQL数据库
      • Java (使用JDBC)

前言

事务的四大特性(ACID特性),即原子性、一致性、隔离性和持久性。“隔离性”确保了在并发环境中,事物的安全可靠。事物的隔离级别对与数据库来说至关重要,而MVCC是实现事物隔离性的重要技术,值得我们探讨一下。

一、事物的隔离级别

数据库事务的隔离级别定义了在多事务并发环境中,一个事务对数据进行读取或修改时,与其他事务的隔离程度。这主要是为了处理并发控制中可能出现的问题,如脏读、不可重复读和幻读。根据ACID(原子性、一致性、隔离性、持久性)原则中的隔离性要求,SQL标准定义了以下四种主要的事务隔离级别:

  1. 读未提交(Read Uncommitted)

    • 这是最低的隔离级别,允许一个事务读取另一个事务尚未提交的数据(脏读)。
    • 优点:并发度最高。
    • 缺点:可能导致脏读、不可重复读和幻读问题。
  2. 读已提交(Read Committed)

    • 事务只能读取已经提交的数据,避免了脏读问题。
    • 优点:可以防止脏读。
    • 缺点:仍可能出现不可重复读和幻读问题。
  3. 可重复读(Repeatable Read)

    • 保证了在一个事务中多次读取同一数据的结果是一致的,即在事务开始后,不会看到其他事务对该数据的修改。
    • MySQL的InnoDB存储引擎默认采用此隔离级别,并通过Next-Key Locks机制尽量避免幻读的发生。
    • 优点:避免了脏读和不可重复读。
    • 缺点:在某些数据库中(如标准的SQL定义),仍可能遇到幻读问题。
  4. 串行化(Serializable)

    • 最高的隔离级别,通过完全的顺序执行事务或者加锁来防止所有并发问题,确保事务之间完全隔离。
    • 优点:能避免脏读、不可重复读和幻读。
    • 缺点:并发度最低,因为事务是串行执行的,可能导致严重的性能下降。

选择合适的隔离级别需要权衡并发性能与数据一致性之间的关系。在实际应用中,可根据业务需求和数据库特性来决定使用哪种隔离级别。例如,对于金融交易系统,可能倾向于选择较高的隔离级别以确保数据的绝对一致性,即使牺牲一定的并发性能。而在读多写少的场景下,可重复读或读已提交可能是更合适的选择。

二、隔离级别是如何实现的

实现事务的隔离级别主要依靠数据库管理系统(DBMS)内部的机制,这些机制确保了在多事务并发环境中数据的正确性和一致性。不同的隔离级别通过不同的策略来控制并发访问,具体实现方式包括但不限于锁定技术、多版本并发控制(MVCC)、乐观锁和悲观锁等。

1. 锁定技术

  • 读未提交(Read Uncommitted):很少直接使用锁来实现,因为这种级别允许脏读,通常不是通过锁定而是依靠数据的自然状态。
  • 读已提交(Read Committed):可以通过短时的行级锁来实现,读取数据前锁定,读取后立即释放。这样可以确保读到的都是已提交的数据。
  • 可重复读(Repeatable Read):通常使用行级锁加上意向锁(如MySQL的Next-Key Locks)来实现,锁定读取的行以及可能插入的新行范围,防止其他事务修改或插入影响当前事务的可重复读。
  • 串行化(Serializable):最严格的隔离级别,可以通过在整个事务期间持有读取到的所有行上的共享锁,以及在更新时持有的排他锁来实现,这几乎等同于串行执行事务。

2. 多版本并发控制(MVCC)

MVCC(多版本并发控制,Multiversion Concurrency Control)是一种数据库管理系统中用于管理并发事务的技术,旨在提高并发性能并维持事务的隔离性。

基本原理

MVCC的核心思想是在数据库中保存数据的多个版本,使得不同事务可以读取到符合其隔离级别的数据版本,而无需对数据加锁。当事务进行读操作时,看到的并不是数据的实时状态,而是该事务开始时刻数据库的一个快照视图。这样,读事务与写事务之间可以并行执行,大大提高了系统的并发能力。

实现机制
  1. 数据版本管理:每条记录除了实际数据外,还会有额外的元数据记录事务的版本信息,如事务ID或时间戳。

  2. Undo Log(回滚日志):MVCC通常依赖Undo Log来实现数据的多版本。当一个事务更新一条记录时,原始数据不会被直接修改或删除,而是将新值写入,并在Undo Log中记录旧值及其相关信息。这样,通过Undo Log可以还原出数据的任何历史版本。

  3. Read View(读视图):在可重复读(Repeatable Read)隔离级别下,事务开始时会创建一个读视图,记录当前活跃的事务ID列表。当事务进行读操作时,根据读视图判断哪些版本的数据对当前事务可见。

  4. 事务隔离级别实现

    • 读未提交(Read Uncommitted):直接读取最新的数据,忽略MVCC机制。
    • 读已提交(Read Committed):每次查询都生成一个新的读视图,只看到已提交的事务产生的数据版本。
    • 可重复读(Repeatable Read):事务开始时创建一个固定的读视图,整个事务期间看到的数据版本不变。
    • 串行化(Serializable):虽然理论上可以通过MVCC实现,但实际上大多数数据库会通过其他机制(如锁)来实现严格的串行化。
优缺点

优点

  • 高并发:通过避免读写锁的冲突,提高了数据库的并发处理能力。
  • 事务隔离性:有效解决了脏读、不可重复读等问题,根据隔离级别提供不同程度的数据一致性保障。
  • 无锁读:读操作无需等待写锁,减少锁竞争,提高读性能。

缺点

  • 存储和管理开销:需要额外的空间来存储数据的多个版本和Undo Log,管理这些版本也会增加系统复杂度。
  • 性能影响:在高并发写入场景下,Undo Log的增长速度可能会对性能造成影响。
  • 数据清理:需要定期清理不再需要的旧版本数据,否则会导致空间占用过大。

3. 乐观锁与悲观锁

  • 乐观锁:适用于并发写相对较少的场景,事务在更新数据前假设不会有冲突,仅在提交时检查数据是否被其他事务修改过,如有冲突则回滚重试。乐观锁可以通过版本号或时间戳字段实现。
  • 悲观锁:假定会发生并发冲突,因此在事务开始时就锁定资源,阻止其他事务访问,直到当前事务结束。悲观锁通常用于隔离级别较高的场景,通过显式锁定机制实现。

实现事务隔离级别通常需要数据库管理系统提供相应的机制,并且可以通过编程接口来选择和配置这些隔离级别,以满足不同应用场景对数据一致性和并发性的需求。

三、MySQL设置隔离级别

MySQL数据库

  • 会话级别设置

    SET SESSION TRANSACTION ISOLATION LEVEL <level>;
    

    其中<level>可以是READ UNCOMMITTEDREAD COMMITTEDREPEATABLE READSERIALIZABLE之一。

  • 全局级别设置(需要管理员权限):

    SET GLOBAL TRANSACTION ISOLATION LEVEL <level>;
    

Java (使用JDBC)

在Java中,通过JDBC连接数据库时,可以使用Connection对象的setTransactionIsolation方法设置事务隔离级别:

Connection conn = DriverManager.getConnection(DB_URL, USER, PASS);
conn.setTransactionIsolation(Connection.TRANSACTION_READ_COMMITTED);

这里的Connection.TRANSACTION_READ_COMMITTED等常量对应不同的隔离级别。


### 注意事项- 设置事务隔离级别应在事务开始之前完成。
- 提高隔离级别通常意味着更强的数据一致性,但可能牺牲并发性能。
- 不同的DBMS在处理隔离级别的细节上可能有差异,尤其是关于幻读的处理。
- 在选择隔离级别时,要充分考虑业务需求和潜在的并发问题,进行适当的平衡。了解和选择正确的事务隔离级别对于设计高效、稳定的数据库应用程序至关重要。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/844399.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Git标签的使用

天行健&#xff0c;君子以自强不息&#xff1b;地势坤&#xff0c;君子以厚德载物。 每个人都有惰性&#xff0c;但不断学习是好好生活的根本&#xff0c;共勉&#xff01; 文章均为学习整理笔记&#xff0c;分享记录为主&#xff0c;如有错误请指正&#xff0c;共同学习进步。…

结巴分词原理

结巴分词是一种中文分词算法&#xff0c;采用基于词频和词汇概率的方法对文本进行切割&#xff0c;将连续的中文字符序列切分成有意义的词&#xff0c;结巴分词被称为“高性能的中文分词工具”。 其原理是通过对中文文本进行扫描&#xff0c;利用前缀词典和后缀词典构建起DAG(有…

C语言-----指针数组 \ 数组指针

一 指针数组 用来存放指针的数组 int arr[10]; //整型数组 char ch[5]; //字符数组 int * arr[6]; //存放整型指针的数组 char * arr[5]; //存放字符指针的数组 // 指针数组的应用 int main() {int arr1[] { 1,2,3,4,5 };int arr2[] { 2,3,4,5,6 };int arr3[] { 3,4,…

滴滴一季度营收同比增长14.9%至491亿元 经调整EBITA盈利9亿元

【头部财经】5月29日&#xff0c;滴滴在其官网发布2024年一季度业绩报告。一季度滴滴实现总收入491亿元&#xff0c;同比增长14.9%&#xff1b;经调整EBITA&#xff08;非公认会计准则口径&#xff09;盈利9亿元。其中&#xff0c;中国出行一季度实现收入445亿元&#xff0c;同…

第一课、Power BI 集成Python

1&#xff0c;下载安装python Python软件地址&#xff1a;Welcome to Python.org 双击自定义安装指定位置并勾选配置环境变量。 后续一直往下&#xff0c;安装完成。 检验是否成功&#xff0c;在cmd命令窗口下输入python 即可看到版本。 安装 pip install pandas 和 pip…

深入解析 JSONPath:从入门到精通

码到三十五 &#xff1a; 个人主页 在数据处理和交换领域&#xff0c;JSON已经成为了一种广泛使用的数据格式&#xff0c; 如何有效地查询和操作这些数据也变得越来越重要。在这种情况下&#xff0c;JSONPath 应运而生&#xff0c;成为了一种在JSON数据中定位和提取信息的强大工…

nginx学习记录-防盗链

1. 防盗链的概念 防盗链&#xff0c;顾名思义就是防止盗取链接&#xff0c;这里的链接一般是资源链接。 如图所示&#xff0c;我们访问一个网站时&#xff08;比如百度&#xff09;&#xff0c;我们第一个请求会获得一个html页面&#xff0c;页面中包含各种资源链接&#xff0…

【C++】C++中的比较工具:深入解析std::greater的用法与应用

文章目录 前言&#xff1a;1. greater的定义和功能2. 使用示例3. 实际应用场景3.1. 在 sort 中的使用3.2. 在 priority_queue 使用 总结&#xff1a; 前言&#xff1a; 在C编程中&#xff0c;标准模板库&#xff08;STL&#xff09;提供了强大的工具和算法&#xff0c;以简化和…

产品经理-原型绘制(五)

1. 概念 用线条、图形描绘出的产品框架&#xff0c;也称为线框图&#xff0c;是需求和功能的具体化表现 2. 常用工具 Axure 3. 类别 3.1 草图原型 手绘图稿&#xff0c;修改方便&#xff0c;规划的早期使用 3.2 低保真原型 简单交互&#xff0c;无设计图&#xff0c;无需…

SOLIDWORKS正版软件购买指南

在这个数字化的时代,SOLIDWORKS作为一种卓悦的三维计算机辅助设计&#xff08;CAD&#xff09;工具&#xff0c;赢得了众多设计师和工程领域专家的喜爱。为了帮大家更加快捷方便地掌握这一知名设计工具&#xff0c;本文写了更全面的SOLIDWORKS选购指导&#xff0c;向大家披露选…

第四十七天 | 198.打家劫舍 213.打家劫舍|| 337.打家劫舍|||

题目&#xff1a;198.打家劫舍 怎么确定当前的房间偷还是不偷呢&#xff1f;其实和前两个房间有关系的——动态规划 1.dp数组含义&#xff1a;考虑下标 i 和 i 之前的房间&#xff08;dp[i] 不一定会偷第 i个房间&#xff09;,所能偷的最大的金币 2.动态转移方程&#xff1a…

【Python】解决Python报错:SyntaxError: invalid character in identifier

&#x1f9d1; 博主简介&#xff1a;阿里巴巴嵌入式技术专家&#xff0c;深耕嵌入式人工智能领域&#xff0c;具备多年的嵌入式硬件产品研发管理经验。 &#x1f4d2; 博客介绍&#xff1a;分享嵌入式开发领域的相关知识、经验、思考和感悟&#xff0c;欢迎关注。提供嵌入式方向…

YOLOv7添加注意力机制和各种改进模块

YOLOv7添加注意力机制和各种改进模块代码免费下载&#xff1a;完整代码 添加的部分模块代码&#xff1a; ########CBAM class ChannelAttentionModule(nn.Module):def __init__(self, c1, reduction16):super(ChannelAttentionModule, self).__init__()mid_channel c1 // red…

[Linux系统编程] 静态库与动态库

一.库的概念 库是写好的现有的&#xff0c;成熟的&#xff0c;可以复用的代码。 本质上来说库是一种可执行代码的二进制形式&#xff0c;可以被操作系统载入内存执行。库有两种&#xff1a;静态库&#xff08;.a、.lib&#xff09;和动态库&#xff08;.so、.dll&#xff09;。…

继承--5.29

继承格式&#xff1a; package javatest2;public class people {int age;double workday;public people(int age, double workday) {this.age age;this.workday workday;} }package javatest2;public class student extends people {int studyday;public student(int age, d…

Prompt工程与实践

Prompt工程与实践 一、Prompt与大模型 1.1 大模型的定义 大模型本质上就是一个概率生成模型&#xff0c;该模型的模型参数足够大&#xff0c;并且在训练过程中阅读了非常多的各个领域的语料。这个时候&#xff0c;如果通过一个正确的、有效的指令去引导这个模型&#xff0c;…

【Python Cookbook】S01E03 找到最大最小的N个元素

目录 问题解决方案讨论 问题 如何在一个集合中找到最大或最小的 N 个元素&#xff1f; 解决方案 使用 heapq 模块。 pip install heapqheapq 模块中&#xff0c;有 nlargest() 以及 nsmallest() 两个函数&#xff1a; import heapqnums [1, 8, 23, 2, 7, -4, 8, 18, 42, …

小阿轩yx-Shell编程之正则表达式与文本处理器

小阿轩yx-Shell编程之正则表达式与文本处理器 正则表达式 &#xff08;RegularExpression&#xff0c;RE&#xff09; 正则表达式概述 正则表达式的定义 又称 正规表达式常规表达式 代码中常简写为 regex、regexp 或 RE 正则表达式 使用单个字符串来描述、匹配一系列符…

C++笔试强训day36

目录 1.提取不重复的整数 2.【模板】哈夫曼编码 3.abb 1.提取不重复的整数 链接https://www.nowcoder.com/practice/253986e66d114d378ae8de2e6c4577c1?tpId37&tqId21232&ru/exam/oj 按照题意模拟就行&#xff0c;记得从右往左遍历 #include <iostream> usi…

GPT-4O神器来袭!自动生成Figma设计稿,移动端开发瞬间加速!

2024年5月29日- 近日&#xff0c;一款基于GPT-4O技术的创新工具成功实现根据产品需求文档&#xff08;PRD&#xff09;自动生成Figma设计稿的功能&#xff0c;为移动端应用开发者带来革命性的便捷。据悉&#xff0c;该功能主要针对移动端应用进行优化&#xff0c;并支持使用高质…