演示案例
為何需要樂觀鎖,與悲觀鎖這樣的鎖?
idname
money
1god
1000
假設god同志的賬上有1000元,現在有兩個執行緒同時往他的賬戶上轉錢。
1.a執行緒準備向god賬戶上轉200,讀取到賬戶上有1000元,事務還未提交
2.b執行緒準備向god賬戶上轉100,讀取到賬戶上有1000元,事務也還未提交
3.a執行緒提交了事務,god賬戶上變成了1200元,但是b執行緒此時不知道god賬戶上變成了1200
4.b執行緒隨即也提交了事務,god賬戶上變成了1200,少了100元
因此,加鎖的目的在於保障乙個執行緒修改資料時,這個資料沒有被其他的執行緒修改過
悲觀鎖與樂觀鎖的區別
1.在事務的基礎上,悲觀鎖更適合短事務(長事務導致其他事務一直被阻塞,影響了系統效能),適用於查少改多
2.在事務的基礎上,樂觀鎖更適合長事務,他的本質並不是鎖,而是通過**實現的。適用於查多改少
悲觀鎖的使用案例
在查的時候,對資料進行鎖定。
在資料庫中:for update
在django中:select_for_update()
原生的sql:
1 開啟事務
2 查詢的時候加鎖 ---》 select * from user where id =1 for update
3 結束事務鎖被釋放
django中:
1 開啟事務
2 在查詢的時候 ---》 user.objects.select_for_update().flilter(id=1).first()
3 事務結束鎖被釋放
樂觀鎖的使用案例
樂觀鎖的本質不是鎖。他是通過**來實現鎖的。
方法:先拿到age資料,在修改的時候再次判斷age是否一樣。
(**實現)目的:將這個資料中的age在原來的基礎上+1
1 開啟事務
2 查詢的時候不做任何操作。data = user.objects.flilter(id=1).first()
3 在修在資料的時候。user.objects.filter(id=1,age=data.age).updata(age=data.age+1)
從而在我查詢到我修改的時候,沒有人改動過
4 如果3中的影響行數為0,證明資料被人修改。迴圈再次執行。如果為1,證明資料沒人動過,修改成功
''' 如果是可重複讀,上面的樂觀鎖無效,必須改成read committed'''
資料庫樂觀鎖與悲觀鎖
每次拿資料的時候都會擔心會被別人修改 疑心重很悲觀 所以每次在拿資料的時候都會上鎖。確保自己使用的過程中不會被別人訪問,自己使用完後再解鎖。期間需要訪問該資料的都會等待。每次拿資料的時候都完全不擔心會被別人修改 心態好很樂觀 所以每次在拿資料的時候都不會上鎖。但是在更新資料的時候去判斷該期間是否被別...
資料庫 樂觀鎖與悲觀鎖
總是認為不會產生併發問題,每次去取資料的時候總認為不會有其他執行緒對資料進行修改,因此不會上鎖,但是在更新時會判斷其他執行緒在這之前有沒有對資料進行修改,一般會使用版本號機制或cas操作實現。update table set x x 1,version version 1 where id and ...
資料庫鎖 樂觀鎖 悲觀鎖理解
參考 mysql innodb中,樂觀鎖 悲觀鎖 共享鎖 排它鎖 行鎖 表鎖 死鎖概念的理解 樂觀鎖最簡單的實現就是在表中加乙個版本號欄位如version,每次新增設定為1,更新的時候檢查版本號是否一致,如果不一致就更新失敗。版本一致才能更新,然後將版本號 1。首先資料庫需要關閉自動提交功能,或者說...