Heim >Datenbank >MySQL-Tutorial >Mysql事务隔离级别_MySQL

Mysql事务隔离级别_MySQL

WBOY
WBOYOriginal
2016-06-01 13:00:061525Durchsuche

<code class=" hljs brainfuck">scott@PROD>select * from dept1;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        10 ACCOUNTING     NEW YORK
        20 RESEARCH       DALLAS
        30 SALES          CHICAGO
        50 OPERATIONS     BOSTON
        20 DBA            Bei Jing
<code class=" hljs vbnet">scott@PROD>update dept1 set deptno=21 where dname='DBA';

1 row updated.

scott@PROD>SELECT s.sid, s.serial#,
  2     CASE BITAND(t.flag, POWER(2, 28))
  3        WHEN 0 THEN 'READ COMMITTED'
  4        ELSE 'SERIALIZABLE'
  5     END AS isolation_level
  6  FROM v$transaction t 
  7  JOIN v$session s ON t.addr = s.taddr
  8  AND s.sid = sys_context('USERENV', 'SID');

       SID    SERIAL# ISOLATION_LEVE
---------- ---------- --------------
        41       5973 READ COMMITTED

Oracle数据库支持READ COMMITTED 和 SERIALIZABLE这两种事务隔离级别。
而Mysql支持READ UNCOMMITED,READ COMMITED,REPEATABLE READ,SERIALIZABLE四种事务隔离级别

READ UNCOMMITTED(读取未提交内容)
在read uncommitted隔离级别,所有事物都可以”看到”未提交事物的执行结果。也就是脏读(读取未提交事务)

READ COMMITED (读取提交内容)
ORACLE的默认隔离级别。一个事物开始时,只能”看见”已经提交事务所做的改变,一个事务从开始提交前,所做的任何数据改变都是不可见的,除非已经提交。这种隔离级别也就是不可重复读

REPEATABLE READ (可重读)
repeatable read隔离级别解决了read uncommitted隔离级导致的问题。它确保同一事务的做个实例在并发读取数据时,会”看到”同样的数据行。不过理论上,这会导致另一个棘手的问题:幻读。简单来说,幻读指当用户读取某一范围的数据行时,另一个事务又在该范围内插入了薪行,当用户再读取该范围的数据行时,会发现有新的”还原”行。

SERIALIZABLE (可串行化)
serializable是最高级别的隔离级,它通过强制事务排序,使之不可能相互冲突,从而解决幻读问题。

Mysql默认的隔离级别是:

<code class=" hljs asciidoc">(mysql@localhost) [fandb]> select @@tx_isolation;
+-----------------+
| @@tx_isolation  |
+-----------------+
| REPEATABLE-READ |
+-----------------+
<code class=" hljs asciidoc">session A:
(mysql@localhost) [fandb]> begin;
Query OK, 0 rows affected (0.00 sec)

(mysql@localhost) [fandb]> update per1 set name='fan1' where id=1
    -> ;
Query OK, 1 row affected (0.00 sec)
Rows matched: 1  Changed: 1  Warnings: 0

(mysql@localhost) [fandb]> select * from per1 limit 1;
+----+------+
| id | name |
+----+------+
|  1 | fan1 |
+----+------+
1 row in set (0.00 sec)
A会话更新一行
<code class=" hljs asciidoc">session B:
(mysql@localhost) [fandb]> begin;
Query OK, 0 rows affected (0.00 sec)

(mysql@localhost) [fandb]> select * from per1 limit 1;
+----+------+
| id | name |
+----+------+
|  1 | fan  |
+----+------+
1 row in set (0.00 sec)
此时在B开始事务并查询,id=1的name列并没有变化
<code class=" hljs css">session A:
(mysql@localhost) [fandb]> commit;
Query OK, 0 rows affected (0.00 sec)
接着A会话提交
<code class=" hljs asciidoc">session B:
(mysql@localhost) [fandb]> select * from per1 limit 1;
+----+------+
| id | name |
+----+------+
|  1 | fan  |
+----+------+
1 row in set (0.00 sec)
在去B会话查询,还是没有变化
<code class=" hljs asciidoc">(mysql@localhost) [fandb]> commit;
Query OK, 0 rows affected (0.00 sec)

(mysql@localhost) [fandb]> select * from per1 limit 1;
+----+------+
| id | name |
+----+------+
|  1 | fan1 |
+----+------+
1 row in set (0.00 sec)
只有当B会话事务结束,再次查询记录才会变化
Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn