ANSI/ISO SQL標准定義了4種事務隔離級別,這些隔離級別是根據事務並行出現的4個“現象”定義的。
4個現象是:
1.更新丟失(Lost Update):A和B同時寫
例:
1.事務A將數值改為1並提交;
2.事務B將數值改為2並提交。
這時數據的值為2,事務A所做的更新將會丟失。
解決辦法:對行加鎖,只允許並發一個更新事務。
2.臟讀(dirty read):A改后還未提交,B讀,A又改並提交
例:
1.Mary的原工資為1000, 財務人員將Mary的工資改為了8000(但未提交事務)
2.Mary讀取自己的工資 ,發現自己的工資變為了8000,歡天喜地!
3.而財務發現操作有誤,回滾了事務,Mary的工資又變為了1000, 像這樣,Mary記取的工資數8000是一個臟數據。
3.不可重復讀(nonrepeatable read):A先讀,B再改,A再讀
例:
1.在事務A中,Mary 讀取了自己的工資為1000,操作並沒有完成
2.在事務B中,這時財務人員修改了Mary的工資為2000,並提交了事務.
3.在事務A中,Mary 再次讀取自己的工資時,工資變為了2000
解決辦法:如果只有在修改事務完全提交之后才可以讀取數據,則可以避免該問題。
4.幻讀(phantom read):A改后還未提交,B改其他的,A再查
例:
1.A把所有的“黑色”改為“白色”
2.B把所有的“紅色”改為“黑色”
3.A再查詢黑色,卻發現還有一批。
根據對4個現象的避免程度,事務的4個隔離級別是:
- 1.Read Uncommited :讀未提交數據(會出現臟讀,不可重復讀,幻讀)
- 2.Read Commited :讀已提交的數據(會出現不可重復讀,幻讀)
- 3.Repeatable Read :可重復讀(會出現幻讀)
- 4.Serializable :串行化
四個級別與四種現象的關系是:
英文 |
中文 |
更新丟失 |
臟讀 |
不可重復讀 |
幻讀 |
Read Uncommited |
讀未提交 |
不會出現 |
會出現 |
會出現 |
會出現 |
Read Commited |
讀已提交 |
不會出現 |
不會出現 |
會出現 |
會出現 |
Repeatable Read |
可重復讀 |
不會出現 |
不會出現 |
不會出現 |
會出現 |
Serializable |
串行化 |
不會出現 |
不會出現 |
不會出現 |
不會出現 |
大多數數據庫的默認隔離級別為: Read Commited,如Sql Server , Oracle。
少數數據庫默認的隔離級別為Repeatable Read, 如MySQL InnoDB存儲引擎。