隔離級別的實現原理

2021-09-20 13:57:38 字數 2821 閱讀 2707

排他鎖(exclusive lock) ,   簡稱x鎖。

若事務t對資料物件a加上x鎖,則只允許t讀取和修改a,其他任何事務都不能再對a加任何型別的鎖,直到t釋放a上的鎖。這就保證了其他事務在t釋放a上的鎖之前不能再讀取和修改a。

規則1:寫乙個資料之前加x鎖, 事務提交之後釋放該x鎖。 

共享鎖(share lock) ,簡稱s鎖, 這個鎖和之前的排他鎖x鎖有區別, 主要用於讀取資料。 

如果乙個資料加了x鎖, 就沒法加s鎖,沒法再加x鎖。

如果乙個資料加了s鎖, 就可以加s鎖,沒法再加x鎖。

規則1讀乙個資料之前加s鎖, 讀完之後立刻釋放該s鎖。 

規則2讀乙個資料之前加s鎖, 事務提交之後立刻釋放該s鎖。 

事務1的修改被事務2的修改覆蓋了,事務1的修改像是丟失了。

排他鎖可以解決兩個人同時修改導致的「丟失修改」的問題,事務1修改的時候不能被其他事務修改。

現象:不會丟失資料,事務1還未提交的修改能被事務2讀取。可以讀到沒有提交或者回滾的內容 (髒資料)。

原理:寫資料時加上x鎖,直到事務結束, 讀的時候不加鎖。 

現象:能避免「丟失資料」和「髒資料」,事務1能讀到其他已提交事務的修改,出現「不可重複讀」的問題。

原理:寫資料的時候加上x鎖, 直到事務結束,  讀的時候加上s鎖, 讀完資料立刻釋放。(共享鎖規則1)

現象:能避免「丟失資料」和「髒資料」, 「不可重複讀」三個問題,事務1能讀取到其他事務新插入讀資料,出現「幻讀」的問題。

原理:寫資料的時候加上x鎖,  直到事務結束, 讀資料的時候加s鎖, 也是直到事務結束。(共享鎖規則2)

現象:能避免「丟失資料」和「髒資料」, 「不可重複讀」,「幻讀」四個問題。

原理:嚴格有序執行,事務不能併發執行。 

「序列化」隔離級別,雖然不會出錯,但是效率實在太低了。  避免使用!!

「可重複讀」,雖然會出現幻讀,但是也能忍受。但為了實現可重複讀, 需要在事務中對讀操作加鎖,並且得持續到整個事務結束,效率也一般,可選擇使用。

隔離級別在可重複讀和讀已提交情況下,有沒有可能在在讀的時候不用加鎖,也能實現可重複讀?

mvcc實現了保證可重複讀並在讀資料的時候不需要加鎖操作!! ps:但是在寫資料的時候,mysql還是要加鎖的,防止寫-寫衝突。讀寫不互相等待,能極大地提高資料庫的併發能力啊。

給資料庫裡面的每張表加兩個隱藏的字段:事務id,回滾指標。(事務id就表明這一行資料是哪個事務操作的,事務id是乙個遞增的數字,每次開始新事務,這個數字就會增加。)

擴充套件乙個read view的資料結構記錄版本資料,它有三個部分:

(1) 當前活躍的事務列表 ,即[101,102]

(2) tmin ,就是活躍事務的最小值, 在這裡 tmin = 101 

(3) tmax, 是系統中最大事務id(不管事務是否提交)加上1。 在這裡例子中,tmax = 103

(注: 在可重複讀的隔離級別下,當第乙個read操作發生的時候,read view就會建立。 在read committed隔離級別下,每次發出read操作,都會建立新的read view。)

原始資料

事務id

回滾指標

name

age 

100null

sf30

開啟兩個事務

事務id101

事務id102

開始事務    標記1

select * from users where name='sf';

開始事務

do others things

update users set age = 35 where name='sf';  標記2

提交事務

select * from users where name='sf';

在標號1 的地方,資料是這樣的:  與此同時,需要建立乙個叫做read view的資料結構。

事務id

回滾指標

name

age 

100null

sf30

事務id

回滾指標

name

age 

102上一版本的資料

sf35

按照可重複讀的要求,事務1無論讀多少次總能讀到age=30的那行記錄,即使事務2修改了age,也不受影響。

那麼如何用來判斷這些資料版本記錄中哪些對你來說是可見的(可讀的)。 」

對於上面的例子,readview 中事務列表是[101,102], tmin= 101, tmax = 103,第一次讀和第二次讀是什麼樣子。

當事務101第一次讀的時候,只有一條記錄, tid = 100 ,小於tmin,所以是可以讀的。 然後事務102做了修改。

當事務101第二次讀的時候,tid=102,程式走到了『tid是否在read view中這一分支,由於102確實在read view的活動事務列表中,那就順著回滾指標找到下一行記錄,即tid為100那一行,再次判斷,這就和第一次讀一樣了。

隔離級別的實現原理

排他鎖 exclusive lock 簡稱x鎖。若事務t對資料物件a加上x鎖,則只允許t讀取和修改a,其他任何事務都不能再對a加任何型別的鎖,直到t釋放a上的鎖。這就保證了其他事務在t釋放a上的鎖之前不能再讀取和修改a。規則1 寫乙個資料之前加x鎖,事務提交之後釋放該x鎖。共享鎖 share loc...

MySQL事務隔離級別的實現原理

在mysql的眾多儲存引擎中,只有innodb支援事務,所有這裡說的事務隔離級別指的是innodb下的事務隔離級別。讀未提交 乙個事務可以讀取到另乙個事務未提交的修改。這會帶來髒讀 幻讀 不可重複讀問題。基本沒用 讀已提交 乙個事務只能讀取另乙個事務已經提交的修改。其避免了髒讀,但仍然存在不可重複讀...

MySQL事務隔離級別的實現原理

在mysql的眾多儲存引擎中,只有innodb支援事務,所有這裡說的事務隔離級別指的是innodb下的事務隔離級別。讀未提交 乙個事務可以讀取到另乙個事務未提交的修改。這會帶來髒讀 幻讀 不可重複讀問題。基本沒用 讀已提交 乙個事務只能讀取另乙個事務已經提交的修改。其避免了髒讀,但仍然存在不可重複讀...