日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > 数据库 >内容正文

数据库

MySQL - 共享锁和排它锁初探

發布時間:2025/3/21 数据库 21 豆豆
生活随笔 收集整理的這篇文章主要介紹了 MySQL - 共享锁和排它锁初探 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

文章目錄

  • 生猛干貨
  • 官方文檔
  • 事務隔離級別
  • 共享鎖 VS 排他鎖的區別
  • SELECT ... FOR UPDATE 排它鎖 演示
  • SELECT ... LOCK IN SHARE MODE 共享鎖 演示
  • 搞定MySQL

生猛干貨

帶你搞定MySQL實戰,輕松對應海量業務處理及高并發需求,從容應對大場面試


官方文檔

鎖定某一行可以用lock in share mode(共享鎖) 和for update(排它鎖)

官方文檔:

https://dev.mysql.com/doc/refman/5.7/en/innodb-locking-reads.html

大體過一下

如果你在查詢數據,然后在同一個事務里插入或者修改相關的數據,常規的 select 語句不會提供足夠的保護。其他的事務可以修改或者刪除你正在查詢的行。

InnoDB 支持兩種可以提供安全機制的讀取鎖:

  • SELECT … LOCK IN SHARE MODE 在讀取的行上設置一個共享鎖,其他的session可以讀這些行,但在你的事務提交之前不可以修改它們。如果這些行里有被其他的還沒有提交的事務修改,你的查詢會等到那個事務結束之后使用最新的值

  • 索引搜索遇到的記錄,SELECT … FOR UPDATE 會鎖住行及任何關聯的索引條目,和你對那些行執行 update 語句相同。其他的事務會被阻塞在對這些行執行 update 操作,獲取共享鎖,或從某些事務隔離級別讀取數據等操作。 一致性讀(Consistent Nonlocking Reads)會忽略在讀取視圖上的記錄的任何鎖。(舊版本的記錄不能被鎖定;它們通過應用撤銷日志在記錄的內存副本上時被重建。)

所有被共享鎖和排他鎖查詢所設置的鎖都會在事務提交或者回滾之后被釋放。

注:

  • 使用 SELECT FOR UPDATE 為 update 操作鎖定行,只適用于 autocommit 被禁用(當使用 START TRANSACTION 開始事務或者設置 autocommit 為0時)。

  • 如果 autocommit 已啟用,符合規范的行不會被鎖定。


事務隔離級別

默認的 RR

mysql> show variables like '%iso%'; +-----------------------+-----------------+ | Variable_name | Value | +-----------------------+-----------------+ | transaction_isolation | REPEATABLE-READ | +-----------------------+-----------------+ 1 row in setmysql>

共享鎖 VS 排他鎖的區別

  • SELECT … LOCK IN SHARE MODE :共享鎖(S鎖, share locks)。其他事務可以讀取數據,但不能對該數據進行修改,直到所有的共享鎖被釋放。

    如果事務對某行數據加上共享鎖之后,可進行讀寫操作;其他事務可以對該數據加共享鎖,但不能加排他鎖,且只能讀數據,不能修改數據

  • SELECT … FOR UPDATE:排他鎖(X鎖, exclusive locks)。如果事務對數據加上排他鎖之后,則其他事務不能對該數據加任何的鎖。獲取排他鎖的事務既能讀取數據,也能修改數據

普通 select 語句默認不加鎖,而CUD操作默認加排他鎖。


SELECT … FOR UPDATE 排它鎖 演示

對所在行加上了一把排它鎖 x鎖

【實驗步驟】

session1session2
begin 模擬開啟事務
select * from country where countrycode = ‘CN’ for update ; --讀取成功,但未提交事務
begin 模擬開啟事務
select * from country where countrycode = ‘CN’ for update ; ---- 可以讀取成功
update country set countryname=‘新中國’ where countrycode = ‘CN’; ---- 一直被阻塞,如果會話一一直沒提交,session2 直到超時,拋出如下異常 1205 - Lock wait timeout exceeded; try restarting transaction

【結論】

通過上述實驗 ,我們可以推斷出其他session只能讀該行數據,修改則會被阻塞,直到鎖定行的session提交事務


SELECT … LOCK IN SHARE MODE 共享鎖 演示

session1session2
begin 模擬開啟事務
select * from country where countrycode = ‘CN’ lock in share mode ; --讀取成功,但未提交事務
begin 模擬開啟事務
select * from country where countrycode = ‘CN’ lock in share mode ; ---- 可以加共享鎖
select * from country where countrycode = ‘CN’ for update ; ---- 不能加排它鎖 一直被阻塞,
update country set countryname=‘China’ where countrycode = ‘CN’ ; — 修改該行數據也被阻塞,如果事務一還沒提交,一直等到超時 1205 - Lock wait timeout exceeded; try restarting transaction

搞定MySQL

總結

以上是生活随笔為你收集整理的MySQL - 共享锁和排它锁初探的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。