事务

  事务你可以去看概念,我给你说下简单理解。你去斗鱼送礼物,扣了你的鱼丸给主播送了礼物,这俩操作必须是绑定在一起的,不然单个任何一个完成了另外一个没完成都会出问题。对到数据库的操作就是,你花钱,买了礼物,礼物送出去。前面两个步骤就是一个事物,花钱买-礼物发到你库存。然后这东西肯定要写到库里。这么说明白了吧,同样送礼物这个,从你的库存拿走,送给主播,也必须是一致的,必须一起完成。面试时候就照着这个意思大概的发挥吧。

  亦或是你去取钱,事务就是保证在你的钱取出来的同时,你的卡里面扣除了相应的钱。要么你取不出来钱,要么你的卡的钱被扣除了。

  另外,真去面试,你别张嘴就xx概念,什么这个性,那个性,干了几年业务的我估计没几个能真记住这些,你就大致按照自己的想法和理解说说。直接背概念十个有九个会被当培训班出来的,面试不过或者被压工资都是寻常的事。

事务的基本概念

如果一个包含多个步骤的业务操作,被事务管理,那么这些操作要么同时成功,要么同时失败。

操作:

  • 开启事务:start transaction;
  • 回滚:rollback;
  • 提交事务:commit;

案例:

张三和李四各有1000元钱,张三给李四转账500元;

#创建表
CREATE TABLE account(
	id INT PRIMARY KEY AUTO_INCREMENT,
	NAME VARCHAR(10),
	balance DOUBLE
);
#添加数据
INSERT INTO account(NAME,balance) VALUE ('zhangsan',1000),('lisi',1000);

SELECT * FROM account;

#张三给李四转账500元
#张三账户减少500元
UPDATE account SET balance=balance-500 WHERE NAME='zhangsan'; 
#李四账户增加500元
UPDATE account SET balance=balance+500 WHERE NAME='lisi'; 

SELECT * FROM account;

#还原金额balance数据
UPDATE account SET balance=1000;

SELECT * FROM account;

#张三给李四转账500元
#张三账户减少500元
UPDATE account SET balance=balance-500 WHERE NAME='zhangsan'; 
#如果中间出错了,李四账户增加500元就不会成功
这是一个错误语句……
#李四账户增加500元
UPDATE account SET balance=balance+500 WHERE NAME='lisi'; 

SELECT * FROM account;

#还原金额balance数据
UPDATE account SET balance=1000;

SELECT * FROM account;

#张三给李四转账500元,如果出错
#开启事务
START TRANSACTION;
#张三账户减少500元
UPDATE account SET balance=balance-500 WHERE NAME='zhangsan'; 
#如果中间出错了
这是一个错误语句……
#李四账户增加500元
UPDATE account SET balance=balance+500 WHERE NAME='lisi'; 
#如果没有问题,提交事务
COMMIT;
#如果有问题,回滚事务
ROLLBACK;

SELECT * FROM account;

#还原金额balance数据
UPDATE account SET balance=1000;

#张三给李四转账500元,如果没出错
#开启事务
START TRANSACTION;
#张三账户减少500元
UPDATE account SET balance=balance-500 WHERE NAME='zhangsan'; 
#如果中间出错了
#这是一个错误语句……
#李四账户增加500元
UPDATE account SET balance=balance+500 WHERE NAME='lisi'; 
#如果没有问题,提交事务
COMMIT;
#如果有问题,回滚事务
ROLLBACK;

SELECT * FROM account;

事务提交的两种方式

自动提交

  • MySQL就是自动提交的
  • 一条DML(增删改)语句会自动提交一次事务。

手动提交

  • Oracle是默认手动提交的
  • 需要先开启事务,再提交

例:自动提交事务

#没有手动START TRANSACTION;会自动COMMIT;
UPDATE account SET balance=1000;

例:手动提交
手动开启事务(START TRANSACTION;),但未提交(COMMIT;),操作会被回滚(ROLLBACK;)。

#手动开启事务
START TRANSACTION;
UPDATE account SET balance=balance-500 WHERE NAME='zhangsan'; 
UPDATE account SET balance=balance+500 WHERE NAME='lisi'; 
#未提交,自动回滚

修改默认的事务提交方式:

  • 查看事务的默认提交方式
#1代表自动提交,0代表手动提交
SELECT @@autocommit;

#修改默认提交方式
SET @@autocommit=0;
SELECT @@autocommit;

#手动提交得commit,否则不生效
UPDATE account SET balance=30;
COMMIT;
SELECT * FROM account;

事务的四大特征

事务是什么?
事务是作为一个逻辑单元执行的一系列操作,一个逻辑工作单元必须有四个属性,称为 ACID(原子性、一致性、隔离性和持久性)属性,只有这样才能成为一个事务:

原子性
事务必须是原子工作单元;对于其数据修改,要么全都执行,要么全都不执行。
即:是不可分割的最小单位,要么同时成功,要么同时失败。

持久性
事务完成之后,它对于系统的影响是永久性的。该修改即使出现系统故障也将一直保持。
即:当事务结束(提交或回滚)后,数据库会持久化的保存数据。

隔离性
由并发事务所作的修改必须与任何其它并发事务所作的修改隔离。事务查看数据时数据所处的状态,要么是另一并发事务修改它之前的状态,要么是另一 事务修改它之后的状态,事务不会查看中间状态的数据。这称为可串行性,因为它能够重新装载起始数据,并且重播一系列事务,以使数据结束时的状态与原始事务 执行的状态相同。
即:多个事物之间,相互独立,不影响。但实际上多个事物之间是会产生影响的。

一致性
事务在完成时,必须使所有的数据都保持一致状态。在相关数据库中,所有规则都必须应用于事务的修改,以保持所有数据的完整性。事务结束时,所有的内部数据结构(如 B 树索引或双向链表)都必须是正确的。
即:事务操作前后,数据总量不变。
例如:
张三和李四各有1000元,张三给李四转账500元之后,二人总钱数还是2000元;如果操作出现问题,数据会回滚到操作之前的状态(张三和李四各有1000元),二人总钱数还是2000元。

事务的隔离级别

概念: 多个事物之间是隔离的,相互独立的。但是如果多个事务操作同一批数据,则会引发一些问题,设置不同的隔离级别就可以解决这些问题。

存在问题:

  1. 脏读:一个事务,读取到另一个事务中没有提交的数据。

  2. 不可重复读(虚读):在同一个事务中,两次读到的数据不一样。

  3. 幻读:一个事务操作(DML)数据表中所有记录,另一个事务添加了一条数据,则第一个事务查询不到自己的修改。

隔离级别:

  1. read uncommitted:读未提交

    产生的问题:脏读、不可重复读、幻读

  2. read committed:读已提交(Oracle默认)

    产生的问题:不可重复读、幻读

  3. repetable read:可重复读(MySQL默认)

    产生的问题:幻读

  4. serializable:串行化

    可以解决所有的问题

注意:隔离级别从小到大,安全性越来越大,效率越来越低。

#数据库查询隔离级别
SELECT @@tx_isolation;
#数据库设置隔离级别:SET GLOBAL TRANSACTION ISOLATION LEVEL 隔离级别;
#得关闭连接重新打开,才能生效
SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED;

默认隔离级别:

修改后的隔离级别:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值