1. 程式人生 > >InnoDB鎖筆記

InnoDB鎖筆記

1.   InnoDB主要使用行級鎖(row lock),其行鎖是通過在索引項上加鎖而實現的,如果MySQL的執行計劃沒有用到索引,那麼行鎖也就無意義了

 

鎖模式:

S鎖: 允許一個事務去讀一行,阻止其他事務獲得相同資料集的排他鎖。

X鎖: 允許獲得排他鎖的事務更新資料,阻止其他事務取得相同資料集的共享讀鎖和排他寫鎖。

意向鎖:資料庫需要對細粒度的物件上鎖,需要首先給粗粒度的物件上鎖。在粗粒度物件上上的鎖成為意向鎖。innodb的意向鎖包括共享意向表鎖和排他意向表鎖。

IS鎖: 對記錄加S鎖之前必須先獲取表的IS鎖

IX鎖: 事務對記錄加X鎖之前必須先獲取表的IX鎖

四種鎖的相容矩陣如下:

  

請求模式

當前模式

X

IX

S

IS

X

衝突

衝突

衝突

衝突

IX

衝突

相容

衝突

相容

S

衝突

衝突

相容

相容

IS

衝突

相容

相容

相容

意向鎖就是表級鎖,會跟表鎖之間有衝突。

行鎖包括:

  • 間隙鎖(Gap Lock),只鎖間隙。表現為鎖住一個區間(注意這裡的區間都是開區間,也就是不包括邊界值)。GAP鎖的目的,是為了防止同一事務的兩次當前讀,出現幻讀的情況.
  • 記錄鎖(Record Lock),只鎖記錄。表現為僅僅鎖著單獨的一行記錄。
  • Next-Key鎖(原始碼中稱為Ordinary Lock),同時鎖住記錄和間隙。從實現的角度為record lock+gap lock,而且兩種鎖有可能只成功一個,所以next-key是半開半閉區間,且是下界開,上界閉。一張表中的next-key鎖包括:(負無窮大,最小的第一條記錄],(記錄之間],(最大的一條記錄,正無窮大)。[對於行的查詢,都是採用該方法,主要目的是解決幻讀的問題
    ]
  • 插入意圖鎖(Insert Intention Lock),插入操作時使用的鎖。在程式碼中,插入意圖鎖實際上是Gap鎖上加了一個LOCK_INSERT_INTENTION的標記。也就是說insert語句會對插入的行加一個X記錄鎖,但是在插入這個行的過程之前,會設定一個Insert intention的Gap鎖,叫做Insert intention鎖。

 

MVCC: 當讀取資料時如果碰到物件已經上了X鎖就直接讀取映象資料。又因為事務隔離級別的不同,在不同事務隔離級別下讀取的映象也會不同。

 

臨鍵鎖:主要是解決幻讀的問題, 是InnoDB的預設行鎖. 

為什麼是使用左開右閉? 因為索引是B+樹, 使用右閉合,是因為新加的資料一般都是存在右邊節點上........

 

 

 

InnoDB的行鎖是通過給索引上的索引(聚集,非聚集)新增鎖來實現的,  

只有通過索引條件進行資料索引, InnoDB才使用行級別鎖, 否則的話會使用表鎖(鎖住所有記錄).

意向鎖: IX,IS是表鎖,更多的時候可以認為是一個標記....

 

 

 

plus:

鎖升級:

很多資料庫如:SQL server就有鎖升級的想象,但是innodb並沒有鎖升級。這是因為innodb根據事務訪問的每個頁對鎖進行管理,採用點陣圖方式,因此不管一個事務鎖住頁中的一行還是多個記錄,其開銷通常都是一樣的。