MySQL 用了哪種默認隔離級別,實現原理是什么?

MySQL 的默認隔離級別是 RR - 可重復讀,可以通過命令來查看 MySQL 中的默認隔離級別。

RR - 可重復讀是基于多版本并發控制(Multi-Version Concurrency Control,MVCC )實現的。MVCC,在讀取數據時通過一種類似快照的方式將數據保存下來,不同事務的 session 會看到自己特定版本的數據,這樣讀鎖和寫鎖就不沖突了。

在 InnoDB 存儲引擎里,在有聚簇索引的情況下,每行數據都包含兩個必要的隱藏列:

  • DB_TRX_ID:記錄某條數據的上次修改它的事務ID(trx_id)
  • DB_ROLL_PTR:回滾指針,指向這條記錄的上一個版本。我們每次對聚簇索引行進行修改時,都會把老版本寫入到undo日志里,這個指針就指向了老版本的位置,當需要進行回滾操作時,事務就通過回滾指針以獲取上一個版本的數據(注意:插入操作的undo日志沒有回滾指針,因為它是新增的數據,沒有老版本;而已刪除的信息會在undo日志記錄的頭信息中存一個delete flag標記,當該標記為true時,表示已刪除,則不返回數據)。

下圖就是一個簡潔的版本鏈概念,InnoDB 中的 undo 日志保存的就是一個版本鏈:

除了版本鏈,我們在實現 MVCC 還用到了另一個概念:read-view,一致性試圖。我們在查詢數據,當使用 select 語句時,InnoDB 會自動生成一個當前活動的(即未提交的)事務 ID 數組,這個 read-view 就是由查詢時所有未提交事務 ID 組成的數組。數組中最小的事務 ID 為 min_id 和已創建的最大事務 ID 為 max_id 組成,查詢的數據結果需要跟 read-view 做比較從而得到快照結果。

我們做查詢時,會查詢出當前 session 的 trx_id,通過和 read-view 比對:

  1. 若 trx_id 比 read-view 中的 min_id ?小,則該版本是已經提交的事務生成,一定可見;
  2. 若 trx_id 比 read view 中的 max_id 大,則該版本是還未提交的事務生成,一定不可見;
  3. 當 trx_id 在 read-view 列表中,即 min_id <= trx_id <= max_id時,如果 trx_id 在 read-view 的數組中,則還未提交,不可見,但是當前事務是可見的;如果 trx_id 不在數組中,表明是已經提交的事務,則該版本可見。

當版本不可見時,需要通過 DB_ROLL_PTR 獲取上一版本的 trx_id,再次比對,直到版本數據可見時,返回結果。

就以上比對的三種情況,用圖示說明下:

transaction 100transaction 101select
update user set name = 'zhangsan' where id = 1
commit
update test set age = 18 where id = 2
select name from use where id=1

1)select 語句執行時,上次更新的 trx_id 為 100,read-view 中未提交的事務為 [101]。此時 read-view 的 min_id 為 101,trx_id 比它小,則該版本是已經提交的事務生成,所以返回 zhangsan。

2)假設當前 select 的 trx_id 為 102,read-view 中未提交的事務為 [101],則需要通過 DB_ROLL_PTR 獲取上一版本的 trx_id 100,注意 trx_id 為 101 的事務是改變了另一張表的數據,所以 undo 日志里版本鏈指向的上一條數據 trx_id 為 100,還是會返回 zhangsan。

3)當 trx_id 在 read-view 中間時:

transaction 100transaction 101select
update user set name = 'zhangsan' where id = 1
commit
update test set name='wangwu' where id = 1
select name from use where id=1

此時 trx_id 為 101,read-view 為 [101],當前事務 ID 在數組中,所以不可見。需要用 DB_ROLL_PTR 找到上一條版本的位置 trx_id 為 100,還是會返回 zhangsan。

RC 隔離級別在查詢時,同一個事務多次查詢,每次會生成獨立的 read-view。而 RR - 可重復讀只在第一次查詢時生成統一的 read view,之后的讀取都復用之前的 read view。而 RU - 讀未提交是可以讀取還沒提交的數據,沒有 undo 版本的概念;可串行化隔離級別在每次讀取時都需要加鎖控制,沒法并發,所以通過版本的概念去控制并發也就沒有意義。

transaction 100transaction 101select
update user set name = 'zhangsan' where id = 1
commit
update test set age = 18 where id = 2
select name from use where id=1
update user set name = '666' where id = 1
select name from use where id=1

當使用 RC 級別時,兩次 select 的 read-view 不一樣,第一次查詢時是 [101],第二次是 [100, 101]。而用 RR 級別時,會復用第一次查詢的 read-view,故多次查詢的結果是一樣的。這也是 MySQL 的隔離級別默認用 RR - 可重復讀的原因之一,不用重復生成 read-view,提升數據庫的操作性能。

總結

每次 select 數據時生成 read view 列表,再配合 undo 日志中的版本鏈,讓不同的事務讀-寫,寫-讀操作可以并發執行,進而實現 MVCC。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/711415.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/711415.shtml
英文地址,請注明出處:http://en.pswp.cn/news/711415.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

視覺三維重建colmap框架的現狀與未來

注&#xff1a;該文章首發3D視覺工坊&#xff0c;鏈接如下3D視覺工坊 前言 眾所周知&#xff0c;三維重建的發展已經進入了穩定期&#xff0c;尤其是離線方案的發展幾乎處于停滯期&#xff0c;在各大論刊上也很少見到傳統sfmmvs亮眼的文章。這也不難理解&#xff0c;傳統的多視…

MYSQL 解釋器小記

解釋器的結果通常通過上述表格展示&#xff1a; 1. select_type 表示查詢的類型 simple: 表示簡單的選擇查詢&#xff0c;沒有子查詢或連接操作 primary:表示主查詢&#xff0c;通常是最外層的查詢 subquery :表示子查詢&#xff0c;在主查詢中嵌套的查詢 derived: 表示派…

【王道數據結構】【chapter8排序】【P360t2】

試編寫一個算法&#xff0c;使之能夠在數組L[1……n]中找出第k小的元素&#xff08;即從小到大排序后處于第k個位置的元素&#xff09;&#xff08;可以直接采用排序&#xff0c;但下面的排序的代碼只是為了方便核對是不是第k小的元素&#xff0c;k從0開始計算&#xff09; #in…

出海手游收入一路高歌,營銷上如何成功?

出海手游收入一路高歌&#xff0c;營銷上如何成功&#xff1f; 以RPG和SLG為代表的中重度游戲一直是國內廠商在海外市場的傳統優勢品類&#xff0c;因為它們具有較高的投資回報率&#xff0c;是國內廠商在國際市場上取得成功的“吸金”利器。 據伽馬數據發布的《2023全球移動游…

SpringCloud搭建微服務之Consul服務配置

1. 概述 前面有介紹過Consul既可以用于服務注冊和發現&#xff0c;也可以用于服務配置&#xff0c;本文主要介紹如何使用Consul實現微服務的配置中心&#xff0c;有需要了解如何安裝Consul的小伙伴&#xff0c;請查閱SpringCloud搭建微服務之Consul服務注冊與發現 &#xff0c…

steam怎么付款

信用卡支付 登錄Steam賬戶&#xff0c;選擇需要購買的游戲或其他物品&#xff0c;點擊“加入購物車”。在購物車頁面點擊“去結賬”按鈕&#xff0c;進入付款頁面。在付款頁面選擇信用卡付款方式&#xff0c;填寫信用卡信息&#xff0c;輸入驗證碼&#xff0c;點擊確認付款。 …

Servlet 新手村引入-編寫一個簡單的servlet項目

Servlet 新手村引入-編寫一個簡單的servlet項目 文章目錄 Servlet 新手村引入-編寫一個簡單的servlet項目一、編寫一個 Hello world 項目1.創建項目2.引入依賴3.手動創建一些必要的目錄/文件4.編寫代碼5.打包程序6.部署7.驗證程序 二、更方便的處理方案&#xff08;插件引入&am…

autocrlf和safecrlf

git遠程拉取及提交代碼&#xff0c;windows和linux平臺換行符轉換問題&#xff0c;用以下兩行命令進行配置&#xff1a; git config --global core.autocrlf false git config --global core.safecrlf true CRLF是windows平臺下的換行符&#xff0c;LF是linux平臺下的換行符。…

98 greenplum 集群搭建過程中碰到的幾個問題

前言 最近有搭建 greenplum 集群的需求 然后 在搭建的過程中碰到了一些問題, 還是有一些時間開銷 并且問題也稍微有些復雜, 因此記錄一下 1. Do not have enough valid segments to start the array. 報錯日志信息如下 20220408:14:15:29:021638 gpstart:gp1:gpadmin-[I…

基于springboot+vue的公交線路查詢系統

博主主頁&#xff1a;貓頭鷹源碼 博主簡介&#xff1a;Java領域優質創作者、CSDN博客專家、阿里云專家博主、公司架構師、全網粉絲5萬、專注Java技術領域和畢業設計項目實戰&#xff0c;歡迎高校老師\講師\同行交流合作 ?主要內容&#xff1a;畢業設計(Javaweb項目|小程序|Pyt…

Find My運動相機|蘋果Find My技術與相機結合,智能防丟,全球定位

運動相機設計用于在各種運動和極限環境中使用&#xff0c;如徒步、登山、攀巖、騎行、滑翔、滑雪、游泳和潛水等&#xff0c;它們通常具有防抖防震、深度防水和高清畫質的特點&#xff0c;能夠適應顛簸劇烈的環境&#xff0c;甚至可以承受一定程度的摔落&#xff0c;一些運動相…

基于systick實現獲取系統運行時間

基于systick實現獲取系統運行時間 文章目錄 基于systick實現獲取系統運行時間systick.c代碼結構:代碼功能:總結 systick.c #include <stdint.h> #include "gd32f30x.h"static volatile uint64_t g_sysRunTime 0;/** ***************************************…

數學建模【聚類模型】

一、聚類模型簡介 “物以類聚&#xff0c; 人以群分”&#xff0c;所謂的聚類&#xff0c;就是將樣本劃分為由類似的對象組成的多個類的過程。聚類后&#xff0c;我們可以更加準確的在每個類中單獨使用統計模型進行估計、分析或預測&#xff0c;也可以探究不同類之間的相關性和…

springboot233大學生就業需求分析系統

大學生就業需求分析系統設計與實現 摘 要 信息數據從傳統到當代&#xff0c;是一直在變革當中&#xff0c;突如其來的互聯網讓傳統的信息管理看到了革命性的曙光&#xff0c;因為傳統信息管理從時效性&#xff0c;還是安全性&#xff0c;還是可操作性等各個方面來講&#xff…

C語言-簡單的環形隊列的源碼示例

概述 環形隊列&#xff08;Circular Queue&#xff09;是一種常見的數據結構&#xff0c;特別適用于在單片機等資源受限的環境下實現緩沖區或隊列功能。下面是一個簡單的環形隊列的源碼示例&#xff0c;用C語言實現&#xff1a; #include <stdio.h> #include <stdint…

五種查看Spring容器中bean的方法

五種查看Spring容器中bean的方法 在Spring應用程序中&#xff0c;了解和查看容器中的Bean是進行調試和問題排查的關鍵。Spring提供了多種方法來查看容器中注冊的Bean&#xff0c;以便我們深入了解應用程序的內部結構和調試潛在問題。本文將介紹五種常用的查看Spring容器中Bean的…

C++ map用法詳細總結40例

文章目錄 1. 定義與初始化2. 插入元素3. 查找元素4. 刪除元素5. 遍歷6. 訪問成員函數7. 修改元素8. 注意事項9. 使用 equal_range 查找鍵值范圍10. 使用 emplace 添加元素11. 使用 cbegin 和 cend 獲取常量迭代器12. 排序規則自定義13. 使用 multimap 存儲重復鍵14. 判斷 map 是…

Python音樂信息管理庫之beets使用詳解

概要 在數字化時代,音樂管理變得越來越重要,特別是對于音樂愛好者和專業音樂人士而言。Python作為一種功能強大的編程語言,擁有著豐富的音樂處理庫,其中Beet就是一款備受推崇的音樂信息管理工具。本文將深入探討Beet庫的功能特性、使用方法以及應用場景,并提供豐富的示例…

市場需求預測模型

市場需求預測模型是一種用于預測某個市場或產品的需求量的數學模型。它基于歷史數據、市場趨勢以及其他相關因素&#xff0c;通過統計和分析的方法來預測未來的市場需求情況。 市場需求預測模型可以幫助企業制定合理的生產計劃、庫存管理和市場營銷策略。通過準確地預測市場需…

python實現數字規整(轉中文)

1.思路根據正則匹配數字類型比如手機號、年月日等進行相對的數字規整 話不多說直接上代碼&#xff0c;有新的類型可以按照當前方案進行新增 import redef match_year_digit(match):m str(match.group())relation {1: 一, 2: 二, 3: 三, 4: 四, 5: 五, 6: 六, 7: 七, 8: 八, …