MySQL语法#2

发布于 2022-02-24  24 次阅读


MySQL语法-事务

9.1事务处理

事务处理在数据库开发过程中有着非常重要的作用,它可以(用于)保证在同一个事务中的操作具有同步性。

9.1.1事务的概念

9.1.2事务的基本操作

在默认情况子啊,用户执行的每一条SQL语句都会当初单独的事务自动提交。如果要将一组SQL 语句作为一个事务,则需要先执行以下语句显式地开启一个事务。

START TRANSACTION; -- 开启显式事务

上述语句执行后,每一条SQL语句不再自动提交,需要使用以下语句手动提交,只有事务提交后其中地操作才会生效。

COMMIT; -- 提交显式事务

若在未提交地情况下执行查询语句,查询到的结果是属于MySQL的4种隔离级别中的READ UNCOMMITTED(读取未提交),这种情况下读取的方式称为脏读即读取脏数据。简而言之,脏读是指一个事务读取了另外一个事务未提交的数据。### 9.2.3MySQL的4种隔离级别

语句执行->写入,COMMIT->提交。

如果不想提交当前事务,可以使用如下语句取消事务(即回滚)。

ROLLBACK; -- 回滚事务

需要注意的是。ROLLBACK只能针对未提交的事务进行回滚,已提交得到事务无法回滚。当执行了COMMIT或者ROLLBACK后,当前事务就会自动结束。

9.1.3事务的保存点

在回滚事务时,事务内的所有操作都将撤销。而若希望只撤销一部分,可以用保存点来实现。

SAVEPOINT 保存点名; -- 在事务中设置一个保存点
ROLLBACK TO SAVEPOINT 保存点名; -- 回滚到指定保存点
RELEASE SAVEPOINT 保存点名; -- 删除保存点

一个事务中可以创建多个保存点,在提交事务后,事务中的保存点就会被删除。另外,在回滚到某个保存点后,在该保存点后设置过的保存点也会消失。

9.1.0拓展

9.1.0.1事务不允许嵌套

若在执行START TRANSACTION语句前上一个事务还未提交,会隐式地执行提交操作。

9.1.0.2事务只针对数据表数据

事务处理不包括创建或删除数据库、数据表,修改表结构等操作,而且执行这类操作时会隐式地执行提交操作。

9.1.0.3支持事务的存储引擎

MySQL5.7默认的存储引擎为InnoDB,该引擎支持事务,而另一个常见得到存储引擎MyISAM不支持事务。对于MyISAM存储引擎的数据表,无论事务是否提交,对数据的操作都会立即生效,不能回滚。

9.1.0.4其它开启事务的方式

在MySQL中,还可以使用START TRANSACTION的别名BEGINBEGIN WORK来显式地开启一个事务,但由于BEGIN与MySQL编程中的BEGIN...END冲突,因此不推荐使用BEGIN

9.1.0.5 事务的自动提交

MySQL默认是自动提交模式,如果没有显式开启事务,每一条SQL语句都会自动提交。如果用户想控制(改变)事务的自动提交方式,可以通过更改AUTOCOMMIT变量来实现,将其值设置为1表示开启自动提交,0表示关闭自动提交。

SELECT @@autocommit;    -- 查看当前会话的AUTOCOMMIT值
SET AUTOCOMMIT = (1 | 0);   -- 更改当前会话的AUTOCOMMIT值,默认为1

改为关闭自动提交后,用户需要手动执行提交操作,才会提交事务。否则,若直接终止MySQL会话,MySQL会自动进行回滚

9.1.0.6控制事务结束后的行为

事务得到提交和回滚还有一些可选得到子句,如下所示。

COMMIT [AND [ NO] CHAIN] [[NO] RELEASE];
ROLLBACK [AND [NO] CHAIN] [[NO] RELEASE];

在上述选项中,AND CHAIN用于在当前事务结束时,立即创建一个新事务,并且新事务与刚刚结束得到事务具有相同的隔离级;RELEASE用于在终止当前事务后,让服务器断开与客户端的连接。若添加NO,则表示抑制CHAINRELEASE的完成。

9.2事务隔离级别

由于数据库是一个多用户的共享资源,MySQL允许多线程并发访问,因此用户可以通过不同得到线程执行不同的事务。为了保证这些事务之间不受影响,对事务设置隔离级别是十分必要的。

9.2.1查看隔离级别

#1.查看全局隔离级
SELECT @@global.transaction_isolation;
#2.查看当前会话(用户会话)的隔离级
SELECT @@session.transaction_isolation;
#3.查看当前会话的下一个事务的隔离级
SELECT @@transaction_isolation;

默认情况下,3条语句返回值应为REPEATABLE-READ,表示隔离级别为可重复读### 9.2.3MySQL的4种隔离级别

9.2.2修改隔离级别

事务的隔离级别可以通过SET语句将进行设置。

SET [SESSION | GLOBAL] TRANSACTION ISOLATION LEVEL 参数值;
# SESSION表示当前会话
# GLOBAL表示全局
# 若省略则表示设置下一个事务的隔离级

参数值可以是READ UNCOMMITTED(读取未提交)、READ COMMITTED(读取提交)、REPEATABLE READ(可重复读)或SERIALIZABLE(可串行化)中的一种。

9.2.3MySQL的4种隔离级别

隔离级别 CN 特点 备注
READ UNCOMMITTED 读取未提交 隔离级别中最低的级别,可以读取未提交的数据(脏读) 几乎不使用
使用读取提交
READ COMMITTED 读取提交 解决了脏读的问题
是大多数DBMS的默认隔离级别(SQL Server、Oracle),不包括MySQL
但是在该级别下会出现不可重复读的问题
不可重复读指的是在一个事务中多次查询结果不一致,原因是数据发生了改变
使用可重复读
REPEATABLE READ 可重复读 解决了不可重复读的问题
理论上会出现幻读(虚读)的问题
但是在MySQL的InnoDB引擎的多版本控制机制中解决了这个问题
可使用可串行化
SERIALIZABLE 可串行化 隔离级别中最高的级别。
它在每个读的数据行加上锁,使之不会发生冲突,从而解决脏读、幻读、不可重复读的问题。
但是加锁可能导致超时和锁竞争现象,因此可串行化也是性能最低的一种隔离级别。
除非为了数据的稳定性
需要减少强制减少并发的情况时
才会选择此种隔离级
SELECT @@innodb_lock_wait_timeout;  -- 查看锁等待的超时时间

9.2.0拓展

9.2.0.1只读事务

#1.设置只读事务
SET [SESSION | GLOBAL] TRANSACTION READ ONLY;
#2.设置读写事务
SET [SESSION | GLOBAL] TRANSACTION READ WRITE;

蔚蓝天空上的无垠,盲目痴愚后的泯然