• SQL中的事务


    目录

    1、概述
    ---1.1事务是什么?
    ---1.2例子:银行转账业务
    ---1.3四个特征ACID
    ---1.4和事务有关的两条SQL语句(TCL)
    ---1.5事务开启和结束的标志

    2、事务的提交和回滚的演示
    ---2.1事务的提交
    ---2.2事务的回滚
    ---2.3手动设置事务开关

    3、事务的隔离级别
    ---3.1read uncommitted 读未提交(级别最低)
    ---3.2read committed 读已提交
    ---3.3repeatable read 可重复读
    ---3.4serializable 串行化(序列化)
    ---3.5查看隔离级别
    ---3.6设置隔离级别
    ---3.7隔离级别不一致性问题的关系

    概述

    事务是什么?

    1、一个最小的不可再分的工作单元;
    2、通常一个事务对应一个完整的业务;(如:银行转账业务)
    3、而一个完整的业务需要批量的DML(insert、update、delete)语句共同完成;
    4、事务只和DML语句有关系,或者说只有DML语句才有事务(保证数据的安全性);
    5、以上所描述的批量DML语句共有多少DML语句,这个和业逻辑有关系,业务逻辑不同DML语句个数不同 。
    6、一些关键词:
    1、开启事务:start transaction
    2、结束事务:end transaction
    3、提交事务:commit transaction
    4、回滚事务:rollback transaction

    例子:银行转账业务

    1、银行转账业务:是一个完整的业务,最小的单元,不可再分。
    2、act-001(50000.0)转10000.0给act-002(10000.0),操作如下:

    update t_act set balance = 40000.0 
    where actno = ‘act-001’;
    update t_act set balance = 20000.0 
    where actno = ‘act-002’;
    

    3、分析
    a)以上两条DML语句必须同时成功或者同时失败,因为它为最小业务单元,不可拆分;
    b)当第一条DML语句执行成功之后,并不能将底层数据库中的第一个账户的数据修改,只是将操作记录了一下,这个记录是在内存中完成的;
    c)当第二条DML语句执行成功之后,和底层数据库文件中的数据完成同步。
    d)若第二条DML语句执行失败,将清空所有的历史操作记录。
    结论:要完成以上功能,必须借助事务(transaction)。

    四个特征ACID

    1、原子性(Atomicity)
    事务是最小单元,不可再分;
    2、一致性(Consistency)
    事务要求所有的DML语句操作的时候,必须保证同时成功或同时失败;
    3、隔离性(Isolation)
    一个事务不会影响其它事务的运行;
    4、持久性(Durability)
    在事务完成之后,该事务对数据库所作的更改将持久地保存在数据库中,并不会被回滚。

    和事务有关的两条SQL语句(TCL)

    1、COMMIT; 提交
    2、ROLLBACK; 回滚

    事务开启和结束的标志
    • 开启的标志
      任何一条DML语句执行,标志事务的开启。
    • 结束的标志
      提交(commit)或者回滚(rollback)
      1、提交:成功的结束,将所有的DML语句操作记录和底层硬盘文件中数据进行一次同步。
      2、回滚:失败的结束,将所有DML语句操作记录全部清空。
    • 重点
      1、在事务进行过程中,未结束之前,DML语句是不会修改底层数据库文件中的数据。
      2、只是将历史操作记录一下,在内存中完成记录。
      3、只有在事务成功结束的时候才会修改底层硬盘文件中的数据。

    事务的提交和回滚的演示

    • 自动提交事务
      在MySQL数据库管理系统中,默认情况下,事务是自动提交的。也就是说,叧要执行一条DML语句,就开启了事务,并且提交了事务。
    事务的提交
    • 第一步:start transaction; 手动开启事务;
      在这里插入图片描述
    • 第二步:DML语句…. 执行批量DML语句;
    INSERT INTO t_user(`name`) 
    VALUES('lisi');
    INSERT INTO t_user(`name`) 
    VALUES('zhaoliu');
    SELECT * FROM t_user;
    

    当前窗口可以查看刚刚插入的数据:
    在这里插入图片描述
    其它窗口则看不见:
    在这里插入图片描述

    • 第三步:commit; 手动提交事务(事务成功结束)。
      在这里插入图片描述
      提交后都能看见:
      在这里插入图片描述
    事务的回滚
    • 第一步:start transaction;手动开启事务
      在这里插入图片描述
    • 第二步:DML语句…..批量DML语句
    INSERT INTO t_user(`name`) 
    VALUES('jack');
    INSERT INTO t_user(`name`) 
    VALUES('rose');
    SELECT * FROM t_user;
    

    当前窗口:
    在这里插入图片描述
    其它窗口:
    在这里插入图片描述

    • 第三步:rollback;手动回滚事务(事务失败结束)
      在这里插入图片描述
      其它窗口:
      在这里插入图片描述
    手动设置事务开关

    1、两种关闭自动提交事务
    a)set autocommit = off;
    b)set session autocommit = off;

    set autocommit = off;
    show variables like '%commit%';
    

    在这里插入图片描述
    2、两种打开自动提交事务
    a)set autocommit = on;
    b)set session autocommit = on;

    set autocommit = on;
    show variables like '%commit%';
    

    在这里插入图片描述
    注意:以上打开或关闭事务只对当前窗口有效。
    3、查询事务状态:show variables like '%commit%';
    在这里插入图片描述

    事务的隔离级别

    事务四个特性ACID之一:隔离性(isolation)

    • 隔离性有四个隔离级别:
      1、read uncommitted 读未提交
      2、read committed 读已提交
      3、repeatable read 可重复读
      4、serializable 串行化
    read uncommitted 读未提交(级别最低)

    1、事务A和和事务B,事务A未提交的数据,事务B可以读取;
    2、这里读取到的数据可以叫做“脏数据”或“脏读 Dirty Read”;
    3、读未提交隔离级别最低,这种级别一般叧在理论上存在,数据库默认隔离级别一般都高于该隔离级别。

    read committed 读已提交

    1、事务A和事务B,事务A提交的数据,事务B才可读取到;
    2、该隔离级别高于“读未提交”级别;
    3、换句话说:对方事务提交之后的数据,当前事务才可读取到;
    4、该隔离级别可以避免脏数据;
    5、该隔离级别能够导致“不可重复读取”(只能读到对方事务提交之后的数据(更新后的),不能读到原来的数据);
    6、Oracle数据库管理系统默认隔离级别为:读已提交。

    repeatable read 可重复读

    1、事务A和事务B,事务A提交之后的数据,事务B读取不到;
    2、事务B是可重复读到数据的;
    3、这种隔离级别高于“读已提交”;
    4、换句话说,对方提交之后的数据,还是读取不到;
    5、这种隔离级别可以避免“脏读和不可重复读”,达到“重复读取”;
    6、MySQL数据库管理系统默认隔离级别为:可重复读;
    7、虽然可以达到“可重复读”效果,但是会导致“幻象读”(只能读到原来的数据)。

    serializable 串行化(序列化)

    1、事务A和事务B,事务A在操作数据库表中数据的时候,事务B只能排队等待(解决了以上所有问题,但是效率太低);
    2、这种事务隔离级别一般很少使用,吞吐量太低,用户体验不好;
    3、这种隔离级别可以避免“幻象读”,每一次读取都是数据库表中真实的记录;
    4、事务A和事务B不再并发。

    查看隔离级别
    • 查看当前会话级隔离级别
      select @@session.transaction_isolation;
      在这里插入图片描述
    • 查看当前全局隔离级别:
      select @@global.transaction_isolation;
      在这里插入图片描述
    设置隔离级别
    • 事务隔离级别的作用范围分为两种:会话级、全局级
      1、会话级(session):只对当前会话有效。
      2、全局级(global):对所有会话有效。
    • 例子
      SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED 事务隔离级别
      事务隔离级别:
      --- READ UNCOMMITTED
      --- READ COMMITTED
      --- REPEATABLE READ
      --- SERIALIZABLE
    SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED
    select @@global.transaction_isolation;
    

    在这里插入图片描述

    隔离级别不一致性问题的关系
    隔离级别 脏读 不可重复读 幻象读
    读未提交
    读已提交 ×
    可重复读 × ×
    串行化 × × ×
  • 相关阅读:
    iOS应用程序间共享数据(转)
    解决右滑返回手势和UIScrollView中的手势冲突(转)
    (转)iOS被开发者遗忘在角落的NSException-其实它很强大
    iOS 身份证最后一位是X,输入17位后自动补全X(转)
    springboot单机秒杀之queue队列
    springboot单机秒杀-aop+锁
    springbot单机秒杀,锁与事务之间的大坑
    spring-cloud学习之4.微服务请求打通
    spring-cloud学习之3.使用feign实现负载均衡
    spring-cloud学习之2.搭建请求网关spring-cloud-getway
  • 原文地址:https://www.cnblogs.com/yu011/p/13354483.html
Copyright © 2020-2023  润新知