成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

怎樣選擇MySQL事務隔離級別?

數據庫 MySQL
對于 Serializable 隔離級別,因為它強制事務串行執行,會在讀取的每一行數據上都加鎖,因此可能會導致大量的超時和鎖爭用的問題。生成環境也不建議使用。

我們回到一個經常會討論的問題:MySQL事務隔離級別究竟應該怎么選擇?

先說一下我自己的見解:

建議在RC和RR兩個隔離級別中選一種,如果能接受幻讀,需要并發高點,就可以配置成RC:

如果不能接受幻讀的情況,就設置成RR隔離級別。

我們就來詳細介紹一下MySQL的4種事務隔離級別。

1 通過基本定義認識事務隔離級別

四種隔離級別的基本定義(如果覺得文字不太好理解,可以結合文章后面的實驗部分):

事務隔離級別

解釋

Read uncommitted

(讀未提交,簡稱:RU)

所有事務都可以看到其它未提交事務的執行結果,這也就是臟讀。

Read Committed

(讀已提交,簡稱:RC)

一個事務只能看見已經提交事務所做的改變,某個事務執行期間可能有其他事務提交,所以可能出現幻讀

Repeatable Read

(可重復讀,簡稱:RR)

這是MySQL的默認事務隔離級別,它確保同一事務相同的語句多次查詢時,會看到同樣的數據行。消除了臟讀、不可重復讀,默認也不會出現幻讀

Serializable

(串行)

這是最高的隔離級別,它通過強制事務排序,使不同事務之間不可能相互沖突,從而解決幻讀問題

解釋一下幻讀:在一個事務里面,按相同的查詢條件重新讀取以前檢索過的數據,卻發現其他事務插入了滿足查詢條件的新數據。這種情況就稱為幻讀。


2 通過實驗認識Read uncommitted

創建測試表和寫入測試數據:

use martin;

drop procedure if exists insert_t21; 
delimiter ;;
create procedure insert_t21() 
begin

drop table if exists t21;

CREATE TABLE `t21` (
`id` int NOT NULL AUTO_INCREMENT,
`a` int NOT NULL,
`b` int NOT NULL,
PRIMARY KEY (`id`),
KEY `idx_c` (`a`)
) ENGINE=InnoDB CHARSET=utf8mb4;
insert into t21(a,b) values (1,1),(2,2);

end;;
delimiter ;


按下圖進行RU隔離級別的實驗:

步驟

session1

session2

1

call insert_t21();


2

set session transaction_isolation='READ-UNCOMMITTED';

set session transaction_isolation='READ-UNCOMMITTED';

3

begin;

begin;

4

select * from t21 where a=1;


5


insert into t21(a,b) values (1,3);

6

select * from t21 where a=1;


7

commit;

commit;

上面的實驗中,第 5 步中 session2 寫入了一條 a、b 值分別為 1、3 的記錄,在第 6 步中,session2 中的事務還沒提交,但是 session1 就能看到 session2 寫入的數據,出現了臟讀現象。


3 通過實驗認識Read Committed

按下圖,進行RC隔離級別的實驗:

ID

session1

session2

1

call insert_t21 ();


2

set session transaction_isolation='READ-COMMITTED';

set session transaction_isolation='READ-COMMITTED';

3

begin;

begin;

4

select * from t21 where a=1;


5


insert into t21(a,b) values (1,3);

6

select * from t21 where a=1;


7


commit;

8

select * from t21 where a=1;


9

commit;



實驗結果是:

session2 寫入了新數據未提交的情況下,session1 無法查看到新記錄,等到 session2 提交之后,session1 才能看到第 5 步 session2 寫入的數據。

但是存在一個問題就是在session1這個事務里面,按相同的查詢條件重新讀取以前檢索過的數據,卻發現其他事務插入了滿足其查詢條件的新數據。也就是出現了幻讀。

4 通過實驗認識Repeatable Read

再來看下RR隔離級別下的實驗:

ID

session1

session2

1

call insert_t21 ();


2

set session transaction_isolation='REPEATABLE-READ';

set session transaction_isolation='REPEATABLE-READ';

3

begin;

begin;

4

select * from t21 where a=1;


5


insert into t21(a,b) values (1,3);

6

select * from t21 where a=1;


7


commit;

8

select * from t21 where a=1;


9

commit;


10

select * from t21 where a=1;


實驗結論:

session2 寫入了新數據未提交的情況下,session1 無法查看到新記錄,等到 session2 提交但是 session1 還未提交時,session1 還是不能看到新記錄,需要等 session1 事務提交之后,才能查看到第 5 步 session2 寫入的新數據。

也就是RR隔離級別下,在同一個事務里面,前后兩條一樣的語句,讀取的數據是一樣的。

5 通過實驗認識Serializable

進行如下實驗:

ID

session1

session2

1

call insert_t21 ();


2

set session transaction_isolation='SERIALIZABLE';

set session transaction_isolation='SERIALIZABLE';

3

begin;

begin;

4

select * from t21 where a=1;


5


insert into t21(a,b) values (1,3);

(等待)

6

select * from t21 where a=1;


7

commit;

session1 提交后,第 5 步中的寫入操作執行成功

8


commit;

9

select * from t21 where a=1;


當 session1 中有事務查詢 a=1 這行記錄時,在 session2 就不能插入 a=1 的記錄,進入等待。必須等 session1 提交后,session2 才能執行成功。也就是讓事務串行進行。

6 Read uncommitted的例子

拿零售業務場景來講,在事務隔離級別 RU 下:

比如顧客 A 在超市買單時,

當收銀員掃完顧客 A 的支付碼后,因為網絡原因,一直等待著(也就是整個支付過程的事務還沒結束);

這時收銀員去后臺數據查詢,看到 A 的錢已經進入超市賬戶了,然后讓顧客 A 離開。

過了一會,整個支付過程回滾了,才發現 A 實際是支付失敗。

這樣超市豈不是很虧。

這就是 RU 隔離級別可能導致臟讀的情況。

7 Read Committed的例子

顧客A在超市購買了90元的東西。

收銀系統查詢到顧客A還剩100元,足夠扣款,

A 的老婆在家網購,花掉了A賬戶里的這100塊,

收銀系統在扣除A賬戶90元時,就會出現報錯,

顧客A肯定郁悶,不是明明錢夠么?

這就是 RC 隔離級別下的幻讀現象。

8 Repeatable Read的例子

顧客A在超市購買了90元的東西。

當收銀系統查詢到顧客A還剩100 元,足夠扣款,

這期間A 的老婆在家網購,能查詢到 A 的賬戶里還有 100 元,但是想要用 A 賬戶里的 100 塊,卻發現并不能使用這 100 元,

A最后的扣款步驟也能正常完成,最終順利完成了整個付款過程,

這就是可重復讀的現象。

9 Serializable的例子

顧客A在超市購買了90元的東西。

當收銀系統查詢到顧客A還剩100元,足夠扣款,

此時A 的老婆在家網購,想查詢 A 賬戶里還有多少錢,卻發現無法查看到,必須要等到 A 整個付款完成,其老婆才能去查詢余額,

這就是串行導致的。

10 如何選擇合適的事務隔離級別

對于RU隔離級別,會導致臟讀,從性能上看,也不會比其它隔離級別好太多,因此生產環境不建議使用。

對于RC隔離級別,相比RU隔離級別,不會出現臟讀;但是會出現幻讀,一個事務中的兩次執行同樣的查詢,可能得到不一樣的結果。

對于 RR 隔離級別,相比RC隔離級別,解決了部分幻讀,我們在鎖那一章也有詳細講解,但是相對于RC,鎖的范圍可能更大了。

對于 Serializable 隔離級別,因為它強制事務串行執行,會在讀取的每一行數據上都加鎖,因此可能會導致大量的超時和鎖爭用的問題。生成環境也不建議使用。

因此總的來說,建議在RC和RR兩個隔離級別中選一種,如果能接受幻讀,需要并發高點,就可以配置成RC,如果不能接受幻讀的情況,就設置成RR隔離級別。

責任編輯:武曉燕 來源: MySQL數據庫聯盟
相關推薦

2025-03-03 08:20:00

MySQL事務隔離數據庫

2018-12-19 16:46:38

MySQL事務隔離數據庫

2021-08-04 13:19:42

MySQL 事務隔離

2021-07-26 10:28:13

MySQL事務隔離

2024-12-02 08:37:04

2009-06-29 17:54:47

Spring事務隔離

2010-11-19 16:13:06

oracle事務隔離級

2021-10-19 10:10:51

MySQL事務隔離級別數據庫

2022-06-10 11:51:49

MySQL事務隔離

2025-01-13 13:12:54

2020-10-13 10:32:24

MySQL事務MVCC

2022-06-29 11:01:05

MySQL事務隔離級別

2021-08-30 20:12:11

MySQL事務隔離

2022-09-13 13:49:05

數據庫隔離

2021-01-18 11:49:26

面試事務隔離

2017-08-09 14:34:12

MysqlJavaPython

2020-09-21 18:44:35

MySQL

2019-10-15 10:23:13

服務器MySQL 數據

2023-02-02 07:06:10

2024-07-16 08:19:46

MySQL數據InnoDB
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 欧美又大粗又爽又黄大片视频 | 国产aaaaav久久久一区二区 | 亚洲精品高清视频在线观看 | 国产一级一级毛片 | 极品久久 | 国产乱一区二区三区视频 | 国产一区二区三区视频 | 激情福利视频 | a级毛片基地 | 自拍偷拍一区二区三区 | 中文字幕高清av | 日本精品一区二区三区视频 | 在线免费亚洲视频 | 欧美一区二区三区国产精品 | 中文字幕乱码一区二区三区 | 狠狠操电影| 亚洲成人av一区二区 | 欧美成人精品在线 | 成人h视频在线观看 | 成人国产a | 99tv| 久久中文字幕在线 | 亚洲h在线观看 | 喷水毛片 | 亚洲欧洲成人av每日更新 | 国产精品久久久久久久久 | 国产精品免费在线 | h在线免费观看 | 国产精品久久久久影院色老大 | 国产精品久久久久久婷婷天堂 | 精品视频一区二区 | 韩国av一区二区 | 91视频在线看 | 中文字幕在线观看视频网站 | 欧美日韩综合一区 | 久久久久国产 | 一本大道久久a久久精二百 欧洲一区二区三区 | 精品一二区 | av中文字幕在线观看 | 国产精品高潮呻吟久久 | 久久人人爽人人爽人人片av免费 |