mysql隔離級(jí)別和鎖的關(guān)系(spring默認(rèn)事務(wù)隔離級(jí)別)
夕逆IT
- 前端設(shè)計(jì)
- 2023-08-13
- 252

大家好,mysql隔離級(jí)別和鎖的關(guān)系相信很多的網(wǎng)友都不是很明白,包括spring默認(rèn)事務(wù)隔離級(jí)別也是一樣,不過(guò)沒(méi)有關(guān)系,接下來(lái)就來(lái)為大家分享關(guān)于mysql隔離級(jí)別和鎖的...
大家好,mysql隔離級(jí)別和鎖的關(guān)系相信很多的網(wǎng)友都不是很明白,包括spring默認(rèn)事務(wù)隔離級(jí)別也是一樣,不過(guò)沒(méi)有關(guān)系,接下來(lái)就來(lái)為大家分享關(guān)于mysql隔離級(jí)別和鎖的關(guān)系和spring默認(rèn)事務(wù)隔離級(jí)別的一些知識(shí)點(diǎn),大家可以關(guān)注收藏,免得下次來(lái)找不到哦,下面我們開(kāi)始吧!
數(shù)據(jù)庫(kù)哪個(gè)隔離級(jí)別可以實(shí)現(xiàn)臟讀
對(duì)于同時(shí)運(yùn)行的多個(gè)事務(wù),當(dāng)這些事務(wù)訪問(wèn)數(shù)據(jù)庫(kù)中相同的數(shù)據(jù)時(shí),如果沒(méi)有采取必要的隔離機(jī)制,就會(huì)導(dǎo)致各種并發(fā)問(wèn)題:?臟讀:對(duì)于兩個(gè)事物T1,T2,T1讀取了已經(jīng)被T2更新但還沒(méi)有被提交的字段.之后,若T2回滾,T1讀取的內(nèi)容就是臨時(shí)且無(wú)效的.?不可重復(fù)讀:對(duì)于兩個(gè)事物T1,T2,T1讀取了一個(gè)字段,然后T2更新了該字段.之后,T1再次讀取同一個(gè)字段,值就不同了.?幻讀:對(duì)于兩個(gè)事物T1,T2,T1從一個(gè)表中讀取了一個(gè)字段,然后T2在該表中插入了一些新的行.之后,如果T1再次讀取同一個(gè)表,就會(huì)多出幾行.數(shù)據(jù)庫(kù)事務(wù)的隔離性:數(shù)據(jù)庫(kù)系統(tǒng)必須具有隔離并發(fā)運(yùn)行各個(gè)事務(wù)的能力,使它們不會(huì)相互影響,避免各種并發(fā)問(wèn)題.一個(gè)事務(wù)與其他事務(wù)隔離的程度稱為隔離級(jí)別.數(shù)據(jù)庫(kù)規(guī)定了多種事務(wù)隔離級(jí)別,不同隔離級(jí)別對(duì)應(yīng)不同的干擾程度,隔離級(jí)別越高,數(shù)據(jù)一致性就越好,但并發(fā)性越弱數(shù)據(jù)庫(kù)提供了4中隔離級(jí)別:隔離級(jí)別描述READUNCOMMITTED(讀未提交數(shù)據(jù))允許事務(wù)讀取未被其他事務(wù)提交的變更,臟讀、不可重復(fù)讀和幻讀的問(wèn)題都會(huì)出現(xiàn)READCOMMITED(讀已提交數(shù)據(jù))只允許事務(wù)讀取已經(jīng)被其他事務(wù)提交的變更,可以避免臟讀,但不可重復(fù)讀和幻讀問(wèn)題仍然會(huì)出現(xiàn)REPEATABLEREAD(可重復(fù)讀)確保事務(wù)可以多次從一個(gè)字段中讀取相同的值,在這個(gè)事務(wù)持續(xù)期間,禁止其他事務(wù)對(duì)這個(gè)字段進(jìn)行更新,可以避免臟讀和不可重復(fù)讀,但幻讀的問(wèn)題依然存在SERIALIZABLE(串行化)確保事務(wù)可以從一個(gè)表中讀取相同的行,在這個(gè)事務(wù)持續(xù)期間,禁止其他事務(wù)對(duì)該表執(zhí)行插入、更新和刪除操作,所有并發(fā)問(wèn)題都可以避免,但性能十分低Oracle支持的2種事務(wù)隔離級(jí)別:READCOMMITED,SERIALIZABLE.Oracle默認(rèn)的事務(wù)隔離級(jí)別為:READCOMMITEDMysql支持4中事務(wù)隔離級(jí)別.Mysql默認(rèn)的事務(wù)隔離級(jí)別為:REPEATABLEREAD
MySQL的可重復(fù)讀級(jí)別能解決幻讀嗎
現(xiàn)在的主流數(shù)據(jù)庫(kù)都使用MVCC,用了之后的RR隔離級(jí)別是不會(huì)出現(xiàn)幻讀的。
不同的資料講的RR是199X年的ANSISQL標(biāo)準(zhǔn),但現(xiàn)實(shí)的數(shù)據(jù)庫(kù)不一定符合標(biāo)準(zhǔn)(事實(shí)上,沒(méi)有幻讀是更好的事情)。
mysql隔離級(jí)別是哪本書(shū)上的
這個(gè)不是書(shū)上的,隔離級(jí)別有,讀已提交,不可重復(fù)讀,可重復(fù)讀,臟讀,幻讀
Java如何實(shí)現(xiàn)對(duì)Mysql數(shù)據(jù)庫(kù)的行鎖
在講鎖之前,首先講講兩個(gè)概念吧,嘿嘿行鎖和MySQL事務(wù)屬性
行鎖
mysql實(shí)現(xiàn)行級(jí)鎖的兩大前提就是,innodb引擎并且開(kāi)啟事務(wù)。由于MySQL/InnoDB的加鎖分析,一般日常中使用方式為:select....fromtablewhere.....forupdate語(yǔ)句并且在RepeatableRead事務(wù)隔離級(jí)別下。
行鎖的劣勢(shì):開(kāi)銷(xiāo)大;加鎖慢;會(huì)出現(xiàn)死鎖
行鎖的優(yōu)勢(shì):鎖的粒度小,發(fā)生鎖沖突的概率低;處理并發(fā)的能力強(qiáng)
加鎖的方式:自動(dòng)加鎖。對(duì)于UPDATE、DELETE和INSERT語(yǔ)句,InnoDB會(huì)自動(dòng)給涉及數(shù)據(jù)集加排他鎖;對(duì)于普通SELECT語(yǔ)句,InnoDB不會(huì)加任何鎖;當(dāng)然我們也可以顯示的加鎖:
共享鎖:select*fromtablewhere“條件”+lockinsharemore
排他鎖:select*fromtablewhere”條件“+forupdate
MySQL事務(wù)屬性
事務(wù)是由一組SQL語(yǔ)句組成的邏輯處理單元,事務(wù)具有ACID屬性。
原子性(Atomicity):事務(wù)是一個(gè)原子操作單元。在當(dāng)時(shí)原子是不可分割的最小元素,其對(duì)數(shù)據(jù)的修改,要么全部成功,要么全部都不成功。
一致性(Consistent):事務(wù)開(kāi)始到結(jié)束的時(shí)間段內(nèi),數(shù)據(jù)都必須保持一致?tīng)顟B(tài)。
隔離性(Isolation):數(shù)據(jù)庫(kù)系統(tǒng)提供一定的隔離機(jī)制,保證事務(wù)在不受外部并發(fā)操作影響的”獨(dú)立”環(huán)境執(zhí)行。
持久性(Durable):事務(wù)完成后,它對(duì)于數(shù)據(jù)的修改是永久性的,即使出現(xiàn)系統(tǒng)故障也能夠保持。
舉例說(shuō)明
innodb引擎中行級(jí)鎖分為以下三種鎖
1.RecordLock
單個(gè)行記錄上的鎖
2.GapLock
間隙鎖,鎖定一個(gè)范圍,不包括記錄本身
3.Next-KeyLock
鎖定一個(gè)范圍和記錄本身
話不多說(shuō)直接代碼開(kāi)干
代碼:select*fromtablewhereorder_no='20200521xxx'forupdate;
order_no是主鍵的時(shí)候,可以確定唯一一條數(shù)據(jù),所以在此加上RecordLock(即為單個(gè)記錄上鎖)
order_no是普通索引的時(shí)候,innodb層面會(huì)根據(jù)條件鎖定一個(gè)范圍,在查詢的時(shí)候聚簇索引上加RecordLock(即為單個(gè)記錄上鎖)
order_no不是索引的時(shí)候,本條sql會(huì)進(jìn)行全表掃描,會(huì)在所有的聚簇索引上加鎖,相當(dāng)于全表鎖,這個(gè)是在mysqlinnodb引擎層面決定。
還有一種情況,假如后面跟多個(gè)情況
代碼:select*fromtablewhereorder_no='20200521'andcode='xxx'forupdate;
經(jīng)過(guò)上面分析
order_no主鍵,code不是索引,查詢都只有一條數(shù)據(jù),加RecordLock
order_no普通索引,code不是索引,會(huì)先掃描order_no='20200521',范圍下加鎖
結(jié)論:我們的forupdate并不時(shí)都鎖一條記錄,也并不是只有一個(gè)鎖,但是也包含我們常用的手段了,在項(xiàng)目中可以實(shí)踐用用哦
好了,如果對(duì)您有幫助,記得關(guān)注收藏轉(zhuǎn)發(fā)哦,我會(huì)一直在這里等候與您交流
Mysql高并發(fā),數(shù)據(jù)亂竄
你說(shuō)的這個(gè),描述過(guò)于簡(jiǎn)單,無(wú)法判斷具體情況。
不過(guò),mysql默認(rèn)的隔離級(jí)別是Repeatableread。會(huì)出現(xiàn)幻讀。如果是Readcommited,會(huì)出現(xiàn)不可重復(fù)讀。
如下:
==============================================================
隔離級(jí)別--------------臟讀---不可重復(fù)讀---幻讀
==============================================================
未提交讀(Readuncommitted)可能可能可能
已提交讀(Readcommitted)不可能可能可能
可重復(fù)讀(Repeatableread)不可能不可能可能
可串行化(Serializable)不可能不可能不可能
==============================================================
什么是不可重復(fù)讀呢?
在一個(gè)事務(wù)中,第一次讀和第二次,有可能讀到的同一條數(shù)據(jù)不一致。
比如:
begin
selectnamefrombwherecol=5;
比如結(jié)果為:xiaoli
updatebsetinfo='abc'wherecol=5andname='xiaoli';
我們并沒(méi)有修改,col=5的name字段,但是再次讀這條數(shù)據(jù)的時(shí)候
selectnamefrombwherecol=5;
這里結(jié)果,可能是'zhangsan'。
commit
為什么這樣呢?當(dāng)你這個(gè)事務(wù)在執(zhí)行的過(guò)程中,其他事務(wù)提交了一個(gè)update,修改了col=5這條數(shù)據(jù)。
什么是幻讀呢?就是在一個(gè)事務(wù)中,已經(jīng)對(duì)符合條件的數(shù)據(jù)進(jìn)行了變更,但是提交前再次讀取的時(shí)候,還會(huì)有滿足要求的數(shù)據(jù),因?yàn)樵谀愕氖聞?wù)過(guò)程中,有其他的事務(wù)進(jìn)行了新數(shù)據(jù)的提交,導(dǎo)致你又出現(xiàn)了滿足條件的數(shù)據(jù)。
比如:
begin
selectcount(*)frombwherecol=5;
比如一共三條
updatebsetcol=10wherecol=5;
提示已經(jīng)更改了3行數(shù)據(jù)。
這時(shí)候已經(jīng)修改但是沒(méi)有提交,
selectcount(*)frombwherecol=5;
發(fā)現(xiàn),又出現(xiàn)了一條。
commit
就會(huì)發(fā)現(xiàn)怎么還有一條沒(méi)有更新到呢?
這就是幻讀。
如果你非要解決這個(gè)問(wèn)題的話,setglobaltransactionisolationlevelserializable;
這種情況下,我在一個(gè)事務(wù)中執(zhí)行的時(shí)候,其他事務(wù)只能等待。哪怕我只執(zhí)行了一個(gè)select語(yǔ)句。
但是這種級(jí)別,基本上談不上高并發(fā),也高并發(fā)不起來(lái)。因此一般生產(chǎn)只能在高并發(fā)和事務(wù)上做一個(gè)平衡。
不知道你說(shuō)的是不是這個(gè)問(wèn)題,這種問(wèn)題需要程序去配合當(dāng)前的事務(wù)級(jí)別。
mysql 的隔離是什么
mysql的隔離就是指,SQL標(biāo)準(zhǔn)定義了四種隔離級(jí)別,用來(lái)限定事務(wù)內(nèi)外的哪些改變是可見(jiàn)的,哪些是不可見(jiàn)的。
譬如,讀取未提交的數(shù)據(jù)【ReadUncommitted】在該隔離級(jí)別,所有的事務(wù)都可以看到其他事務(wù)沒(méi)有提交的執(zhí)行結(jié)果。
還有,讀取提交的內(nèi)容【ReadCommitted】該隔離級(jí)別是大多數(shù)數(shù)據(jù)庫(kù)的默認(rèn)的隔離級(jí)別(不是MySQL默認(rèn)的)。它滿足了隔離的簡(jiǎn)單定義:一個(gè)事務(wù)只能看到其他的已經(jīng)提交的事務(wù)所做的改變。這種隔離級(jí)別也支持不可重復(fù)讀,即同一個(gè)select可能得到不同的結(jié)果。等等
好了,關(guān)于mysql隔離級(jí)別和鎖的關(guān)系和spring默認(rèn)事務(wù)隔離級(jí)別的問(wèn)題到這里結(jié)束啦,希望可以解決您的問(wèn)題哈!
本文鏈接:http://xinin56.com/qianduan/1753.html