阅读 119

MySQL事务隔离级别

这是我参与8月更文挑战的第7天,活动详情查看:8月更文挑战

猫和老鼠.jpg

前言:
本篇文章是我关于MySQL的第七篇文章,水平一般、能力有限。文章写的比较浅,适合新手来看。上一篇文章讲到了事务的由来,本篇介绍事务的隔离级别。

隔离级别介绍

前文中讲MySQL的隔离性时说到,一般情况下事务在未完成时对其他连接是不可见的。但是只是一般情况下,SQL标准中规定了四种隔离级别,每种隔离级别的允许事务间的可见级别是不同的。(每中存储引擎实现的隔离级别也略有不同)

隔离级别越低,可以执行的并发也就越高,性能也就越高。反之,隔离级别越高,执行的并发会低,性能也会低。

查询当前隔离级别

-- 这两种都可以(默认查询的是会话级别,查询系统级别为 global.transaction_isolation
mysql> select @@transaction_isolation;
+-------------------------+
| @@transaction_isolation |
+-------------------------+
| REPEATABLE-READ         |
+-------------------------+
mysql> show variables like 'transaction_isolation';
+-----------------------+-----------------+
| Variable_name         | Value           |
+-----------------------+-----------------+
| transaction_isolation | REPEATABLE-READ |
+-----------------------+-----------------+
复制代码

mysql 8.0之前用

show variables like 'tx_isolation';

修改隔离级别

set session transaction isolation level REPEATABLE READ;
set session transaction isolation level READ COMMITTED;
set session transaction isolation level REPEATABLE READ;
set session transaction isolation level SERIALIZABLE;
复制代码

下面我们来实际体验一下,首先建表和造数据。

CREATE table xuezhong_role (
	name char(4) not null comment '角色名称',
	remark varchar(20) not null comment '评语',
        power smallint NOT NULL COMMENT '武力值'
) ENGINE=InnoDB;

select * from xuezhong_role;

name|remark         |power|
----+---------------+-----+
曹长卿 |天下风流一石,曹长卿独占八斗 |   88|
李淳罡 |天不生我李淳罡,剑道万古如长夜|   95|

复制代码

1.READ UNCOMMITTED(读未提交)

顾名思义就是可以读取到正在执行中,但是还没提交的事务,这也被称之为脏读(Dirty Read)。如果一个连接正在修改的数据还未提交就被读取到是很危险的。并且在性能上并没有提升太多。一般在开发应用场景中用不到。

会话1: 关闭自动提交,开启事务,执行更新。此时事务还未被提交

SET AUTOCOMMIT=0 ;
start transaction; 
update xuezhong_role set power=100 where name ='曹长卿';
复制代码

会话2:修改隔离级别,直接查询。此时查询到了另一个会话中未提交的事务数据。

set session transaction isolation level REPEATABLE READ;
select * from xuezhong_role where name ='曹长卿';
+-----------+--------------------------------------------+-------+
| name      | remark                                     | power |
+-----------+--------------------------------------------+-------+
| 曹长卿    | 天下风流一石,曹长卿独占八斗                |   100 |
+-----------+--------------------------------------------+-------+
复制代码

会话1: 回滚数据

rollback;
复制代码

会话2:再次查询,数据恢复为88

select * from xuezhong_role where name ='曹长卿';
+-----------+--------------------------------------------+-------+
| name      | remark                                     | power |
+-----------+--------------------------------------------+-------+
| 曹长卿    | 天下风流一石,曹长卿独占八斗                |   88 |
+-----------+--------------------------------------------+-------+
复制代码

2. READ COMMITTED(读已提交)

顾名思义就是只能读取到已经执行完的事务,这也是大部分数据库采用的事务隔离级别,例如Oracle。但是MySQL采用的不是这种隔离级别。这种隔离级别又被称之为不可重复读。

3. REPEATABLE READ(可重复读)

MySQL采用的默认级别,执行事务前和后得到的查询结果是一致的。

4. SERIALIZABLE(可串行化)

一般较少采用的隔离级别。

文章分类
后端
文章标签