MySQL事务管理的作用详解
作者:青柠果 发布时间:2024-01-23 21:20:37
1.为何使用事务管理
可以保证数据的完整性。事务(Transaction),就是将一组SQL语句放在同一批次内去执行,如果一个SQL语句出错,则该批次内 的所有SQL都将被取消执行。
例子: 转账为例。
金庸向张无忌转账1000元。----在数据库中修改两个账号的余额。
发生意外情况,则出现金庸减钱成功,而张无忌加钱失败。 如何解决?
使用事务进行解决,此时代码执行后金庸的钱没有减,张无忌的钱也没有加
2.数据库事务的原理
如果不写begin;commit;此时事务默认自动开启,自动提交; 在数据库中 ,事务都是自动提交的。事务的自动提交就是 执行sql语句完成之后 就立刻持久化到数据库中。
begin;开始事务
rollback;回滚事务
commit;提交事务
当我们添加了begin;和commit;后 事务的提交就从自动变成手动。因为中途出错,所以导致 commit;不执行,也就是说缓冲区中的数据没有到持久化 的数据库中 。
public class Test {
public static void main(String[] args) {
Connection connection =null;
try {
Class.forName("com.mysql.cj.jdbc.Driver");
connection= DriverManager.getConnection(
"jdbc:mysql://localhost:3306/mydb?serverTimezone=Asia/Shanghai",
"root","123456");
connection.setAutoCommit(false);//开启事务的手动提交
String sql = "update tb_emp set salary=salary-1000 where name='金庸'";
PreparedStatement ps =connection.prepareStatement(sql);
ps.executeUpdate();
String sql1 = "update tb_emp setsalary=salary+1000 where name='张无忌'";
ps = connection.prepareStatement(sql1);
ps.executeUpdate();
connection.commit();//提交事务
}catch (Exception e){
try {
connection.rollback();//事务回滚 最初的状态
} catch (SQLException throwables) {
throwables.printStackTrace();
}
e.printStackTrace();
}finally{
}
}
}
3.什么是事务
从开启到提交为一个事务。 由此可见,一个事务对应一组业务。一个事务中间可以有一条sql,多条sql。 所以 一个业务开始之前 开启事务 一个业务 结束之后 提交事务。 我们这个转账案例:需要几个事务? 可以写成两个事务,但是不合适。因为我们的需求 让金庸减的同时让张无忌加钱。只能写 成一个事 务。 把多条sql语句当作一件事情,要同时都能执行到。
事务(Transaction),一般是指要做的或所做的事情。在计算机术语 中是指访问并可能更新数据库中各种数据项的一个程序执行单元 (unit)。事务通常由高级数据库操纵语言或编程语言(如SQL,C++或 Java)书写的用户程序的执行所引起,并用形如begin transaction和 end transaction语句(或函数调用)来界定。事务由事务开始 (begin transaction)和事务结束(end transaction)之间执行的全体 操作组成。
概括为: 事务是由一些列动作组成,这些动作要么都执行,要么都不执行。
3.1 事务的特性ACID
1、原子性(Atomicity): 事务开始后所有操作,要么全部做完,要么全部不做,不可能停滞在中间 环节。事务执行过程中 出错,会回滚到事务开始前的状态,所有的操作就 像没有发生一样。也就是说事务是一个不可分 割的整体,就像化学中学过 的原子,是物质构成的基本单位。
2、一致性(Consistency): 事务开始前和结束后,数据库的数据完整性约束没有被破坏,事务前后操 作数据是一致的 。比如 A向B转账,不可能A扣了钱,B却没收到。 能量守恒。
3、隔离性(Isolation): 一个事务的执行不能被其他事务干扰。即一个事务内部的操作及使用的数 据对并发的其他事务是 隔离的,并发执行的各个事务之间不能互相干扰。 比如A正在从一张银行卡中取钱,在A取钱的过 程结束前,B不能向这张卡 转账。 两个事务之间是有隔离级别,隔离级别的不同会导致出现不同的问 题。此时产生三种读: 脏读 幻读 不可重复读。
4、持久性(Durability): 持久性(durability)。持久性也称永久性(permanence),指一个事务 一旦提交,它对数据库 中数据的改变就应该是永久性的。接下来的其他操 作或故障不应该对其有任何影响。
3.2 事务的并发问题
1、脏读:
事务A读取了事务B更新的数据,然后B回滚操作,那么A读取到的数据是脏数据。
2、不可重复读
事务A多次读取同一数据,事务B在事务A多次读取的过程中,对数据作了更新并提交,导致事务A多次读取同一数据时,结果不一致。
3、幻读
已知有两个事务A和B,A从一个表中读取了数据,然后B在该表中插入了一些新数据,导致A再次读取同一个表,就会多出几行,简单的说,一个事务中先后读取一个范围的记录,但每次读取的记录数不同,称之为幻象读。
小结:不可重复读和幻读容易混淆,不可重复读侧重于修改,幻读侧重于新增或删除,解决不可重复读的问题只需锁住满足条件的行,解决幻读需要锁表。
3.3 隔离级别
事务隔离性的等级:
查看事务的隔离等级:
语句:select @@global.transaction_isolation,@@transaction_isolation;
事务的隔离等级有四点,每种隔离等级有其会出现的情况
1.Read Uncommitted(读取未提交内容)
在该隔离级别,所有事务都可以看到其他未提交事务的执行结果。本隔离级别很少用于实际应用,因为它的性能也不比其他级别好多少。读取未提交的数据,也被称之为脏读(Dirty Read)。
2.Read Committed(读取提交内容 也叫做不可重复读)
这是大多数数据库系统的默认隔离级别(但不是MySQL默认的)。它满足了隔离的简单定义:一个事务只能看见已经提交事务所做的改变。这种隔离级别 也支持所谓的不可重复读(Nonrepeatable Read),因为同一事务的其他实例在该实例处理其间可能会有新的commit,所以同一select可能返回不同结果。
一个事务读某条数据读两遍,读到的是不一样的数据,也就是说,一个事务在进行中读取到了其他事务对旧数据的修改结果,(比如说 我开一个事务 修改某条数据 先查后改 执行修改动作的时候发现这条数据已经被别的事务删掉了)
3.Repeatable Read(可重读)
这是MySQL的默认事务隔离级别,它确保同一事务的多个实例在并发读取数据时,会看到同样的数据行。不过理论上,这会导致另一个棘手的问题:幻读 (Phantom Read)。简单的说,幻读指当用户读取某一范围的数据行时,另一个事务又在该范围内插入了新行,当用户再读取该范围的数据行时,会发现有新的“幻影” 行。InnoDB和Falcon存储引擎通过多版本并发控制(MVCC,Multiversion Concurrency Control)机制解决了该问题。
一个事务中,读取到了其他事务新增的数据,仿佛出现了幻象。(幻读与不可重复读类似,不可重复读是读到了其他事务update/delete的结果,幻读是读到了其他事务insert的结果)
4.Serializable(可串行化)
这是最高的隔离级别,它通过强制事务排序,使之不可能相互冲突,从而解决幻读问题。简言之,它是在每个读的数据行上加上共享锁。在这个级别,可能导致大量的超时现象和锁竞争。
隔离级别越高,然后执行效率越低。
4.Spring事务管理
来源:https://blog.csdn.net/qq_50896786/article/details/125663403


猜你喜欢
- 在MySQL里,主键索引和辅助索引分别是什么意思,有什么区别?上次的分享我们介绍了聚集索引和非聚集索引的区别,本次我们继续介绍主键索引和辅助
- 使用matplotlib创建百分比堆积柱状图的思路与堆积柱状图类似,只不过bottom参数累计的不是数值而是百分比,因此,需要事先计算每组柱
- 前言在对DataFrame数据进行处理时,存在需要对数据内容进行遍历的场景。因此记录一下按照行,列遍历的几种方式。一、按行遍历1. 使用lo
- 作为一个.net后台开发的程序猿,博客里既然大多都是前端相关的博文。是不是该考虑换方向了,转前端开发得了 ...小小吐槽一下,近期受该不该跳
- 今天做visual transformer研究的时候,发现了einops这么个神兵利器,决定大肆安利一波。先看链接:https://gith
- 目录背景法1,不适用法2,已不能用法3:Appnium法4:模拟操作整体代码后续工作及扩展总结背景由于课题需要爬取朋友圈的内容作为研究数据,
- 1、项目背景对于不会PS的小伙伴,抠图是一个难度系数想当高的活儿,某宝照片抠图和证件照换底色均价都是5元RMB,所以今天要介绍的这款神工具,
- 本文主要介绍了django admin search_fields placeholder 管理后台添加搜索框提示文字,分享给大家,具体如下
- 当 Yii框架仍处于 RC(候选版)阶段时,我们 对它进行过报道,那时它刚刚全面达到候选版本阶段,(现在它已经发布了正式版本)我们感觉是时候
- 1.过滤器的使用1.过滤器和测试器在Python中,如果需要对某个变量进行处理,我们可以通过函数来实现。在模板中,我们则是通过过滤器来实现的
- 【数据库模型类】class ConColumn(db.Model): __tablename__='con
- 1、获取插入数据的主键idimport pymysqldatabase = pymysql.connect( host=&quo
- 概念MySQL UNION 操作符用于连接两个以上的 SELECT 语句的结果组合到一个结果集合中。多个 SELECT 语句会删除重复的数据
- 一、Spring Boot原理用户从页面前端,也就是我们所说的 view 层进行查询访问,进入到 controller 层找到对应的接口,接
- zipfile模块是python中一个处理压缩文件的模块,解决了不少我们平常需要处理压缩文件的需求 ,本文主要谈谈zipfile几个常用的用
- 在使用PyTorch做实验时经常会用到生成随机数Tensor的方法,比如:torch.rand()torch.randn()torch.no
- 问题介绍棋盘覆盖问题,是一种编程问题。如何应用分治法求解棋盘覆盖问题呢?分治的技巧在于如何划分棋盘,使划分后的子棋盘的大小相同,并且每个子棋
- 我使用的Python3.5,32版本win764位系统,pandas0.19版本,使用df=pd.read_clipboard()的时候读不
- 能够为数据库数据提供的最简单的用户界面之一就是窗体,窗体可以一次性呈现出来自同一记录的各个域。本文通过python3+pyqt5改写实现了p
- pynput这个库让你可以控制和监控输入设备。对于每一种输入设备,它包含一个子包来控制和监控该种输入设备:pynput.mouse:包含控制