什么是臟讀、不可重復(fù)讀、幻讀?
文章已收錄Github精選,歡迎Star:https://github.com/yehongzhi/learningSummary
臟讀、不可重復(fù)讀、幻讀
在現(xiàn)代關(guān)系型數(shù)據(jù)庫(kù)中,事務(wù)機(jī)制是非常重要的,假如在多個(gè)事務(wù)并發(fā)操作數(shù)據(jù)庫(kù)時(shí),如果沒有有效的機(jī)制進(jìn)行避免就會(huì)導(dǎo)致出現(xiàn)臟讀,不可重復(fù)讀,幻讀。
臟讀
1、在事務(wù)A執(zhí)行過程中,事務(wù)A對(duì)數(shù)據(jù)資源進(jìn)行了修改,事務(wù)B讀取了事務(wù)A修改后的數(shù)據(jù)。
2、由于某些原因,事務(wù)A并沒有完成提交,發(fā)生了RollBack操作,則事務(wù)B讀取的數(shù)據(jù)就是臟數(shù)據(jù)。
這種讀取到另一個(gè)事務(wù)未提交的數(shù)據(jù)的現(xiàn)象就是臟讀(Dirty Read)。

不可重復(fù)讀
事務(wù)B讀取了兩次數(shù)據(jù)資源,在這兩次讀取的過程中事務(wù)A修改了數(shù)據(jù),導(dǎo)致事務(wù)B在這兩次讀取出來的數(shù)據(jù)不一致。
這種在同一個(gè)事務(wù)中,前后兩次讀取的數(shù)據(jù)不一致的現(xiàn)象就是不可重復(fù)讀(Nonrepeatable Read)。

幻讀
事務(wù)B前后兩次讀取同一個(gè)范圍的數(shù)據(jù),在事務(wù)B兩次讀取的過程中事務(wù)A新增了數(shù)據(jù),導(dǎo)致事務(wù)B后一次讀取到前一次查詢沒有看到的行。
幻讀和不可重復(fù)讀有些類似,但是幻讀強(qiáng)調(diào)的是集合的增減,而不是單條數(shù)據(jù)的更新。

第一類更新丟失
事務(wù)A和事務(wù)B都對(duì)數(shù)據(jù)進(jìn)行更新,但是事務(wù)A由于某種原因事務(wù)回滾了,把已經(jīng)提交的事務(wù)B的更新數(shù)據(jù)給覆蓋了。這種現(xiàn)象就是第一類更新丟失。

第二類更新丟失
其實(shí)跟第一類更新丟失有點(diǎn)類似,也是兩個(gè)事務(wù)同時(shí)對(duì)數(shù)據(jù)進(jìn)行更新,但是事務(wù)A的更新把已提交的事務(wù)B的更新數(shù)據(jù)給覆蓋了。這種現(xiàn)象就是第二類更新丟失。

事務(wù)隔離級(jí)別
為了解決以上的問題,主流的關(guān)系型數(shù)據(jù)庫(kù)都會(huì)提供四種事務(wù)的隔離級(jí)別。事務(wù)隔離級(jí)別從低到高分別是:讀未提交、讀已提交、可重復(fù)讀、串行化。事務(wù)隔離級(jí)別等級(jí)越高,越能保證數(shù)據(jù)的一致性和完整性,但是執(zhí)行效率也越低。所以在設(shè)置數(shù)據(jù)庫(kù)的事務(wù)隔離級(jí)別時(shí)需要做一下權(quán)衡,MySQL默認(rèn)是可重復(fù)讀的級(jí)別。
讀未提交
讀未提交(Read Uncommitted),是最低的隔離級(jí)別,所有的事務(wù)都可以看到其他未提交的事務(wù)的執(zhí)行結(jié)果。只能防止第一類更新丟失,不能解決臟讀,可重復(fù)讀,幻讀,所以很少應(yīng)用于實(shí)際項(xiàng)目。
讀已提交
讀已提交(Read Committed), 在該隔離級(jí)別下,一個(gè)事務(wù)的更新操作結(jié)果只有在該事務(wù)提交之后,另一個(gè)事務(wù)才可能讀取到同一筆數(shù)據(jù)更新后的結(jié)果。可以防止臟讀和第一類更新丟失,但是不能解決可重復(fù)讀和幻讀的問題。
可重復(fù)讀
可重復(fù)讀(Repeatable Read),MySQL默認(rèn)的隔離級(jí)別。在該隔離級(jí)別下,一個(gè)事務(wù)多次讀同一個(gè)數(shù)據(jù),在這個(gè)事務(wù)還沒結(jié)束時(shí),其他事務(wù)不能訪問該數(shù)據(jù)(包括了讀寫),這樣就可以在同一個(gè)事務(wù)內(nèi)兩次讀到的數(shù)據(jù)是一樣的。可以防止臟讀、不可重復(fù)讀、第一類更新丟失、第二類更新丟失的問題,不過還是會(huì)出現(xiàn)幻讀。
串行化
串行化(Serializable),這是最高的隔離級(jí)別。它要求事務(wù)序列化執(zhí)行,事務(wù)只能一個(gè)接著一個(gè)地執(zhí)行,不能并發(fā)執(zhí)行。在這個(gè)級(jí)別,可以解決上面提到的所有并發(fā)問題,但可能導(dǎo)致大量的超時(shí)現(xiàn)象和鎖競(jìng)爭(zhēng),通常不會(huì)用這個(gè)隔離級(jí)別。
總結(jié)
下面我們對(duì)事務(wù)的隔離級(jí)別和對(duì)并發(fā)問題的解決情況,請(qǐng)看下圖:

這篇文章就講到這里了,感謝大家的閱讀,希望看完大家能有所收獲!
覺得有用就點(diǎn)個(gè)贊吧,你的點(diǎn)贊是我創(chuàng)作的最大動(dòng)力~
我是一個(gè)努力讓大家記住的程序員。我們下期再見!!!
能力有限,如果有什么錯(cuò)誤或者不當(dāng)之處,請(qǐng)大家批評(píng)指正,一起學(xué)習(xí)交流!
