分布式鎖的三種實(shí)現(xiàn)方式

注:轉(zhuǎn)載請注明出處:http://www.reibang.com/p/d93a4f98067e

分布式鎖的實(shí)現(xiàn)原理也是面試的一大考點(diǎn)享郊,現(xiàn)就其進(jìn)行總結(jié)如下:

1:為什么需要分布式鎖仪芒?

首先我們應(yīng)該先了解一下分布式鎖的使用場景泉手,然后再來理解為什么需要分布式鎖∶淄現(xiàn)我舉兩個例子來進(jìn)行闡述:
應(yīng)用場景:
1:銀行轉(zhuǎn)賬問題(該場景不太好解釋):A在上海宙项,B在北京同時在建行轉(zhuǎn)賬給杭州C鲸阻,A轉(zhuǎn)賬時切诀,會修改C處服務(wù)器的表诬留,B不能在此刻轉(zhuǎn)賬斜纪,同理,B轉(zhuǎn)賬時文兑,A不能做處理盒刚,A,B的轉(zhuǎn)賬操作時同步绿贞,必須保證數(shù)據(jù)的一致性因块,這就需要分布式鎖來進(jìn)行處理。
2:取任務(wù)問題:某服務(wù)提供一組任務(wù)籍铁,A系統(tǒng)請求隨機(jī)從任務(wù)組中獲取一個任務(wù)涡上;B系統(tǒng)請求隨機(jī)從任務(wù)組中獲取一個任務(wù)。 在理想的情況下寨辩,A從任務(wù)組中挑選一個任務(wù)吓懈,任務(wù)組刪除該任務(wù),B從剩下的的任務(wù)中再挑一個靡狞,任務(wù)組刪除該任務(wù)耻警。 同樣的,在真實(shí)情況下甸怕,如果不做任何處理甘穿,可能會出現(xiàn)A和B挑中了同一個任務(wù)的情況。

2:為什么分布式系統(tǒng)中不能用普通鎖呢梢杭?那么普通鎖和分布式鎖有什么區(qū)別呢温兼?

普通鎖:單一系統(tǒng)中,同一個應(yīng)用程序是有同一個進(jìn)程武契,然后多個線程并發(fā)會造成數(shù)據(jù)安全問題募判,他們是共享同一塊內(nèi)存的荡含,所以在內(nèi)存某個地方做標(biāo)記即可滿足需求,例如synchronized和volatile+cas一樣對具體的代碼做標(biāo)記届垫,對應(yīng)的就是在同一塊內(nèi)存區(qū)域作了同步的標(biāo)記释液。
分布式鎖:分布式系統(tǒng)中,最大的區(qū)別就是不同系統(tǒng)中的應(yīng)用程序都是在各自機(jī)器上不同的進(jìn)程中處理的装处,這里的線程不安全可以理解為多進(jìn)程造成的數(shù)據(jù)安全問題误债,他們不會共享同一臺機(jī)器的同一塊內(nèi)存區(qū)域,因此需要將標(biāo)記存儲在所有進(jìn)程都能看到的地方妄迁。例如zookeeper作分布式鎖寝蹈,就是將鎖標(biāo)記存儲在多個進(jìn)程共同看到的地方,redis作分布式鎖登淘,是將其標(biāo)記公共內(nèi)存箫老,而不是某個進(jìn)程分配的區(qū)域。

3:分布式鎖的三種實(shí)現(xiàn)方式

注:用何種分布式鎖以公司為主黔州。

a:zookeeper實(shí)現(xiàn)分布式鎖(用的最多)

實(shí)現(xiàn)方式:
方案1:利用節(jié)點(diǎn)名稱的唯一性來實(shí)現(xiàn)共享鎖槽惫。
算法思路: 利用名稱唯一性,加鎖操作時辩撑,只需要所有客戶端一起創(chuàng)建/test/Lock節(jié)點(diǎn),只有一個創(chuàng)建成功仿耽,成功者獲得鎖合冀。解鎖時,只需刪除/test/Lock節(jié)點(diǎn)项贺,其余客戶端再次進(jìn)入競爭創(chuàng)建節(jié)點(diǎn)君躺,直到所有客戶端都獲得鎖。
方案2:利用臨時順序節(jié)點(diǎn)實(shí)現(xiàn)共享鎖开缎。(主要是用這種方式實(shí)現(xiàn))
算法思路:對于加鎖操作棕叫,可以讓所有客戶端都去/lock目錄下創(chuàng)建臨時順序節(jié)點(diǎn),如果創(chuàng)建的客戶端發(fā)現(xiàn)自身創(chuàng)建節(jié)點(diǎn)序列號是/lock/目錄下最小的節(jié)點(diǎn)奕删,則獲得鎖俺泣。否則,監(jiān)視比自己創(chuàng)建節(jié)點(diǎn)的序列號小的節(jié)點(diǎn)(比自己創(chuàng)建的節(jié)點(diǎn)小的最大節(jié)點(diǎn))完残,進(jìn)入等待伏钠。
比如創(chuàng)建節(jié)點(diǎn):/lock/0000000001、/lock/0000000002谨设、/lock/0000000003熟掂。則節(jié)點(diǎn)/lock/0000000001會先獲得鎖,因?yàn)閦k上的節(jié)點(diǎn)是有序的扎拣,且都是最小的節(jié)點(diǎn)先獲得鎖赴肚。
注:臨時順序節(jié)點(diǎn)比持久順序節(jié)點(diǎn)的好處是:當(dāng)zookeeper宕機(jī)后素跺,臨時順序節(jié)點(diǎn)會自動刪除,獲取鎖的客戶端會釋放鎖誉券,不會一直造成鎖等待指厌,而持久節(jié)點(diǎn)會造成鎖等待。
兩種方式的區(qū)別
方案1會產(chǎn)生驚群效應(yīng):假如許多客戶端在等待一把鎖横朋,當(dāng)鎖釋放時候所有客戶端都被喚醒仑乌,然后競爭分布式鎖,僅僅有一個客戶端得到鎖琴锭。
方案2是按照創(chuàng)建順序排隊(duì)的實(shí)現(xiàn)晰甚,多個客戶端共同等待鎖,當(dāng)鎖釋放時只有一個客戶端會被喚醒决帖,在zk上注冊節(jié)點(diǎn)最小的客戶端會被喚醒厕九,避免了驚群效應(yīng)。

b:redis實(shí)現(xiàn)分布式鎖(用的次之)

redis實(shí)現(xiàn)分布式鎖主要靠四個命令:
setnx(set if not exits 維護(hù)著是樂觀鎖):當(dāng)不存在key的時候地回,才為key設(shè)置值為value扁远。setnx與set的區(qū)別:set是存在key,則去覆蓋value刻像;setnx是不存在key畅买,則重新給key和value賦值。
getset:根據(jù)key得到舊的值细睡,并set新的值谷羞。
expire:設(shè)置過期時間。
del:刪除

實(shí)現(xiàn)方式(文字配合圖片可更加清晰):
1:獲取鎖的時候溜徙,使用setnx加鎖湃缎,并使用expire命令為鎖添加一個超時時間,超過該時間則自動釋放鎖蠢壹,鎖的value值為一個隨機(jī)生成的UUID嗓违,通過此在釋放鎖的時候進(jìn)行判斷。
2:獲取鎖的時候還設(shè)置一個獲取的超時時間图贸,若超過這個時間則放棄獲取鎖蹂季。
3:釋放鎖的時候,通過UUID判斷是不是該鎖求妹,若是該鎖乏盐,則執(zhí)行delete進(jìn)行鎖釋放。


redis實(shí)現(xiàn)分布式鎖

c:數(shù)據(jù)庫實(shí)現(xiàn)分布式鎖(用的最少)

實(shí)現(xiàn)方式:利用的是樂觀鎖和悲觀鎖
樂觀鎖:在表中添加版本號的字段制恍,每次更新前都先查詢出帶版本號的數(shù)據(jù)父能,然后再更新的時候where條件語句后帶版本號條件,更新成功表示鎖已占用净神,更新不成功表示鎖沒被占用何吝。
悲觀鎖:利用select...for update(X鎖)/select...lock in share mode(S鎖)溉委,一般來說用X鎖的較多,因?yàn)楹罄m(xù)多會做寫功能的實(shí)現(xiàn)爱榕。
注:當(dāng)實(shí)現(xiàn)悲觀鎖的時候瓣喊,需要關(guān)閉數(shù)據(jù)庫的事務(wù)自動提交機(jī)制不然不會生效。因此java代碼中應(yīng)該選擇主動關(guān)閉數(shù)據(jù)庫的事務(wù)自動提交功能黔酥。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末藻三,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子跪者,更是在濱河造成了極大的恐慌棵帽,老刑警劉巖,帶你破解...
    沈念sama閱讀 206,968評論 6 482
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件渣玲,死亡現(xiàn)場離奇詭異逗概,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)忘衍,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,601評論 2 382
  • 文/潘曉璐 我一進(jìn)店門逾苫,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人枚钓,你說我怎么就攤上這事铅搓。” “怎么了搀捷?”我有些...
    開封第一講書人閱讀 153,220評論 0 344
  • 文/不壞的土叔 我叫張陵狸吞,是天一觀的道長。 經(jīng)常有香客問我指煎,道長,這世上最難降的妖魔是什么便斥? 我笑而不...
    開封第一講書人閱讀 55,416評論 1 279
  • 正文 為了忘掉前任至壤,我火速辦了婚禮,結(jié)果婚禮上枢纠,老公的妹妹穿的比我還像新娘像街。我一直安慰自己,他們只是感情好晋渺,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,425評論 5 374
  • 文/花漫 我一把揭開白布镰绎。 她就那樣靜靜地躺著,像睡著了一般木西。 火紅的嫁衣襯著肌膚如雪畴栖。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,144評論 1 285
  • 那天八千,我揣著相機(jī)與錄音吗讶,去河邊找鬼燎猛。 笑死,一個胖子當(dāng)著我的面吹牛照皆,可吹牛的內(nèi)容都是我干的重绷。 我是一名探鬼主播,決...
    沈念sama閱讀 38,432評論 3 401
  • 文/蒼蘭香墨 我猛地睜開眼膜毁,長吁一口氣:“原來是場噩夢啊……” “哼昭卓!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起瘟滨,我...
    開封第一講書人閱讀 37,088評論 0 261
  • 序言:老撾萬榮一對情侶失蹤候醒,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后室奏,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體火焰,經(jīng)...
    沈念sama閱讀 43,586評論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,028評論 2 325
  • 正文 我和宋清朗相戀三年胧沫,在試婚紗的時候發(fā)現(xiàn)自己被綠了昌简。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 38,137評論 1 334
  • 序言:一個原本活蹦亂跳的男人離奇死亡绒怨,死狀恐怖纯赎,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情南蹂,我是刑警寧澤犬金,帶...
    沈念sama閱讀 33,783評論 4 324
  • 正文 年R本政府宣布,位于F島的核電站六剥,受9級特大地震影響晚顷,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜疗疟,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,343評論 3 307
  • 文/蒙蒙 一该默、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧策彤,春花似錦栓袖、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,333評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至庞瘸,卻和暖如春捧弃,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背擦囊。 一陣腳步聲響...
    開封第一講書人閱讀 31,559評論 1 262
  • 我被黑心中介騙來泰國打工塔橡, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留梅割,地道東北人。 一個月前我還...
    沈念sama閱讀 45,595評論 2 355
  • 正文 我出身青樓葛家,卻偏偏與公主長得像户辞,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子癞谒,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,901評論 2 345