事務的四種隔離級別

事務指定四種類型的隔離級別,隔離程度按照從弱到強分別爲
  • Read Uncommitted讀未提交
  • Read Committed讀已提交
  • Repeatable Read可重複讀
  • Serializable串行化
數據不一致的幾個體現
  • Dirty Read - 髒讀
如果一個事務中對數據進行了更新,但事務還沒有提交,另一個事務可以“看到”該事務沒有提交的更新結果,這樣造成的問題就是,如果第一個事務回滾,那麼,第二個事務在此之前所“看到”的數據就是一筆髒數據。
不可重複讀取
  • Non-Repeatable Read - 不可重複讀取
是指同一個事務在整個事務過程中對同一筆數據進行讀取,每次讀取結果都不同。如果事務1在事務2的更新操作之前讀取一次數據,在事務2的更新操作之後再讀取同一筆數據一次,兩次結果是不同的,所以,Read Uncommitted也無法避免不可重複讀取的問題。
  • Phantom Read - 幻讀
幻讀是指同樣一筆查詢在整個事務過程中多次執行後,查詢所得的結果集是不一樣的。幻讀針對的是多筆記錄。在Read Uncommitted隔離級別下, 不管事務2的插入操作是否提交,事務1在插入操作之前和之後執行相同的查詢,取得的結果集是不同的,所以,Read Uncommitted同樣無法避免幻讀的問題。
                                                                                              
Read Uncommitted.  
最低的隔離級別,Read Uncommitted最直接的效果就是一個事務可以讀取另一個事務並未提交的更新結果。

Read Uncommitted是以較低的隔離度來尋求較高的性能,其本身無法Dirty Read - 髒讀、Non-Repeatable Read - 不可重複讀取、Phantom Read - 幻讀

Read Committed.  
Read Committed通常是大部分數據庫採用的默認隔離級別,它在Read Uncommitted隔離級別基礎上所做的限定更進一步, 在該隔離級別下,一個事務的更新操作結果只有在該事務提交之後,另一個事務纔可能讀取到同一筆數據更新後的結果。 所以,Read Committed可以避免Read Uncommitted隔離級別下存在的髒讀問題, 無法避免不可重複讀取和幻讀的問題。

Repeatable Read.
Repeatable Read隔離級別可以保證在整個事務的過程中,對同一筆數據的讀取結果是相同的,不管其他事務是否同時在對同一筆數據進行更新,也不管其他事務對同一筆數據的更新提交與否。 Repeatable Read隔離級別避免了髒讀和不可重複讀取的問題,但無法避免幻讀(MySQL innodb的間隙鎖可以避免,但是容易造成性能下降和死鎖)

Serializable.
最爲嚴格的隔離級別,所有的事務操作都必須依次順序執行,可以避免其他隔離級別遇到的所有問題,是最爲安全的隔離級別, 但同時也是性能最差的隔離級別,因爲所有的事務在該隔離級別下都需要依次順序執行,所以,併發度下降,吞吐量上不去,性能自然就下來了。 因爲該隔離級別極大的影響系統性能,所以,很少場景會使用它。通常情況下,我們會使用其他隔離級別加上相應的併發鎖的機制來控制對數據的訪問,這樣既保證了系統性能不會損失太大,也能夠一定程度上保證數據的一致性。
__________________________________________________________
對於數據庫來說,通常都有一個默認的隔離級別,大多數情況下都是Read Committed,只有Hsqldb使用Read UnCommited作爲默認隔離級別。 而且,並非所有的數據庫都支持這四種隔離級別,比如Oracle只支持Read Committed和Serializable,如果你指定的隔離級別當前數據庫不支持的話, 數據庫會採用默認的隔離級別代替你指定的隔離級別。EJB,Spring,JDBC等數據訪問方式都允許我們爲事務指定以上提到的四種隔離級別,但最終事務是否以指定的隔離級別執行,則由底層的數據資源來決定。
發佈了37 篇原創文章 · 獲贊 20 · 訪問量 9萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章