MYSQL-InnoDB邏輯存儲結構 詳解

InnoDB邏輯存儲結構

段—區—頁—行

表空間:

默認情況下InnoDB有一個共享表空間ibdata1,所有數據放入這個表空間,如果開啟了innodb_file_per_table(默認ON),每張表都可以放到一個單獨的表空間,但只把數據、索引和Insert Buffer Bitmap放入單獨表空間,其它數據,如undo信息、插入緩沖索引頁、事務信息,二次寫緩沖等還是放共享表空間

段:

表空間由各個段組成,數據段、索引段、回滾段等,數據段即B+樹葉子節點索引段即B+樹非葉子節點。每個段開始時,先用32個頁大小的碎片頁存放數據,使用完這些碎片頁,再去一個區一個區地申請內存,這保證了小段如undo這樣的段可以省空間

區:

區由連續的頁組成,一個區固定是1MB,頁默認16KB,即一個區有64個連續的頁,InnoDB1.0.x引入壓縮頁,頁的大小可以是2K、4K、8K,但不管怎么變,區都是1MB

頁:

InnoDB磁盤最小的管理單位,默認16KB,InnoDB1.2.x開始可以更改默認大小innodb_page_size為4K、8K、16K,更改后,不得再次修改,除非mysqldump導入導出產生新的庫

常見的頁類型:

  • 數據頁(B-tree Node)
  • undo頁(undo Log Page)
  • 系統頁(System Page)
  • 索引頁(Index Page)
  • 事務數據頁(Transaction system Page)
  • 插入緩沖位圖頁(Insert Buffer Bitmap)
  • 插入緩沖空閑列表頁(Insert Buffer Free List)
  • 未壓縮的二進制大對象頁(Uncompresses BLOB Page)
  • 壓縮的二進制大對象頁(compressed BLOB Page)

行:

行存儲有四種格式,Redundant、Compact、Dynamic和Compressed。MySQL5.1開始默認使用Compact,MySQL5.7開始默認使用Dynamic

? Compact:

在這里插入圖片描述

? 變長字段長度列表:當數據表有變長字段時才出現,記錄本行中各變長字段實際長度,當長度小于255時用1個字節表 示,大于255時用2個字節表示,不會用3個字節,因為變長字段有長度限制,最多65535字節

? NULL標志位:當數據表存在允許NULL的字段時才出現,本行每個字段是否為null用0或1表示,同時必須是整數個字 節大小,即不足8個bit位的高位補0

? 記錄頭信息:存儲一些信息,固定5個字節,如delete_mask,標識刪除位;next_record下條記錄的地址; record_type,記錄類型,0為普通,1為B+樹非葉子節點,2為最小記錄,3為最大記錄

? 變長字段長度列表和NULL是逆序存儲(方便尋址)

? row_id:當建表時沒指定主鍵時,選擇第一個非空唯一索引當主鍵,如果沒有,添加該列作為主鍵,6字節大小

? trx_id:事務id,這條數據是哪個事務生成的,6字節大小

? roll_ptr:上個版本的指針,7字節大小

? 一個頁最多有16KB,16384字節,而varchar(n)最多可以存儲65533字節,那么一個頁可能都放不了一條記錄,這時就會行溢出,溢出的數據會放到“溢出頁”中,原頁會保留20個字節指向該溢出頁的地址。

? Compressed和Dynamic行格式和Compact非常相似,主要是行溢出時的處理,這兩個不會在原頁保存數據,只用20字節指針指向溢出頁,數據全在溢出頁,而Compressed還會對BLOB、TEXT、VARCHAR這些大長度類型的數據進行zlib算法壓縮

char和varchar?

char存儲固定長度字符串,最大長度255字節,當存儲長度小于定義的長度時,MySQL在后面補空格(如果本身存儲的字符串尾部就有空格,就會丟失空格信息!)

varchar存儲可變字符串,讀取速度相對更慢一點,因為需要先讀長度,再讀數據

一般使用varchar存儲較好,但考慮到極端情況,varchar因為長度可變,可能出現頁分裂的情況

如果是身份證號、訂單號、國家編碼等這些固定長度的,可以用char

如果是產品描述、用戶地址、用戶名稱這種,可以用varchar

數據頁結構:


在這里插入圖片描述
在這里插入圖片描述

采用鏈表的結構是讓數據頁之間不需要是物理上的連續的,而是邏輯上的連續。

數據頁中的記錄按照「主鍵」順序組成單向鏈表,單向鏈表的特點就是插入、刪除非常方便,但是檢索效率不高,最差的情況下需要遍歷鏈表上的所有節點才能完成檢索。

因此,數據頁中有一個頁目錄,起到記錄的索引作用,就像我們書那樣,針對書中內容的每個章節設立了一個目錄,想看某個章節的時候,可以查看目錄,快速找到對應的章節的頁數,而數據頁中的頁目錄就是為了能快速找到記錄。

在這里插入圖片描述

  • 將所有的記錄劃分成幾個組,這些記錄包括最小記錄最大記錄,但不包括標記為“已刪除”的記錄;
  • 每個記錄組的最后一條記錄就是組內最大的那條記錄,并且最后一條記錄的頭信息中會存儲該組一共有多少條記錄,作為 n_owned 字段(上圖中粉紅色字段)
  • 頁目錄用來存儲每組最后一條記錄的地址偏移量,這些地址偏移量會按照先后順序存儲起來,每組的地址偏移量也被稱之為槽(slot),每個槽相當于指針指向了不同組的最后一個記錄。

從圖可以看到,頁目錄就是由多個槽組成的,槽相當于分組記錄的索引。然后,因為記錄是按照「主鍵值」從小到大排序的,所以我們通過槽查找記錄時,可以使用二分法快速定位要查詢的記錄在哪個槽(哪個記錄分組),定位到槽后,再遍歷槽內的所有記錄,找到對應的記錄,無需從最小記錄開始遍歷整個頁中的記錄鏈表。

  • 第一個分組中的記錄只能有 1 條記錄;
  • 最后一個分組中的記錄條數范圍只能在 1-8 條之間;
  • 剩下的分組中記錄條數范圍只能在 4-8 條之間。

索引:

在這里插入圖片描述

索引頁的行記錄是指針,指向一個頁,索引頁的索引鍵值就是指向的頁的最小索引鍵值

數據頁的行記錄就是數據(聚簇索引,如果是二級索引,存放的是主鍵值)

頁合并和頁分裂:

? 頁合并:

? 當一個數據頁的使用率低于一定閾值(50%)時,MySQL 就會將該頁與相鄰的空閑頁合并成一個頁面。

? 例如,數據頁能存放7條數據,有兩個相鄰的數據頁,一個存儲 [1, 2, 3, 4],另一個是[5, 6]。當刪除4時,會檢查 本頁,本頁數據只有三條,小于閾值,MySQL 就會將兩個頁面合并成一個頁面,存儲的數據變成 [1, 2, 3, 5, 6]

? 頁分裂:

? 當一個數據頁已經滿了,而有新的數據要插入到該頁時,MySQL 就會進行頁分裂操作。

? 例如,數據頁能存放5條數據,假設一個數據頁已經存儲了 [1, 2, 3, 4, 5],而有新的數據6要插入到該頁中, MySQL 就會將該頁拆分為兩個頁面,一個頁面存儲 [1, 2, 3],另一個頁面存儲 [4, 5, 6]。

? 頁分裂是為了保證插入順序的同時不大量挪動數據

? 采用邏輯刪除可以減少頁合并

? 采用批量順序插入可以減少頁分裂

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

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

相關文章

[特殊字符] Python 批量合并 Word 表格中重復單元格教程(收貨記錄案例實戰)

在日常辦公中,Word 表格中常出現重復的“供應商名稱”或“物料編碼”,會導致表格冗余且視覺混亂。這時候,用 Python 自動合并重復單元格可以大幅提升表格專業度和可讀性。本篇給大家演示如何用 python-docx 實現該功能。 ? 功能概覽 自動讀取…

從零構建Node.js服務托管前端項目

下面是一個完整的指南,教你如何從零開始構建一個Node.js服務來托管前端項目,并代理API請求到其他服務器。 1. 項目初始化 # 創建項目目錄 mkdir node-proxy-server cd node-proxy-server# 初始化npm項目 npm init -y# 安裝必要依賴 npm install expres…

Lynx vs React Native vs Flutter 全面對比:三大跨端框架實測分析

一文看懂三大熱門跨端技術的歷史淵源、架構機制、開發體驗、包體積對比與性能評估。 我陪你用實測數據帶你理性選型,不踩坑,不盲信。 1. 框架簡介:它們是誰?來自哪里?干嘛用? 框架名稱所屬公司發布時間初衷…

CKESC的ROCK 180A-H 無人機電調:100V 高壓冗余設計與安全保護解析

一、核心技術參數與性能指標 電壓范圍:支持 12~26S 鋰電(適配 110V 高壓系統)電流特性: 持續工作電流:90A(特定散熱條件)瞬時耐流(1 秒):220A,3 …

優化 ArcPy 腳本性能

使用并行處理 如果硬件條件允許,可以使用 Python 的并行處理模塊(如 multiprocessing)來同時處理多個小任務。這樣可以充分利用多核處理器的優勢,提高腳本的執行效率。 import multiprocessing def process_raster(raster):arcpy…

Windows下CMake通過鴻蒙SDK交叉編譯三方庫

前言 華為鴻蒙官方的文章CMake構建工程配置HarmonyOS編譯工具鏈 中介紹了在Linux平臺下如何使用CMake來配置鴻蒙的交叉編譯環境,編譯輸出在Harmony中使用的第三方so庫以及測試demo。 本文主要是在Windows下實現同樣的操作。由于平臺差異的原因,有些細節…

從C學C++(6)——構造函數和析構函數

從C學C(6)——構造函數和析構函數 若無特殊說明,本博客所執行的C標準均為C11. 構造函數與析構函數 構造函數定義 構造函數是特殊的成員函數,當創建類類型的新對象,系統自動會調用構造函數構造函數是為了保證對象的每個數據成員都被正確初…

清理 Windows C 盤該注意什么

C 盤空間不足會嚴重影響系統性能。 清理 C 盤文件時,首要原則是安全。錯誤地刪除系統文件會導致 Windows 無法啟動。下面我將按照 從最安全、最推薦到需要謹慎操作的順序,為你詳細列出可以清理的文件和文件夾,并提供操作方法。 第一梯隊&…

Python Selenium 滾動到特定元素

文章目錄 Python Selenium 滾動到特定元素?? **1. 使用 scrollIntoView() 方法(最推薦)**🖱? **2. 結合 ActionChains 移動鼠標(模擬用戶行為)**🧩 **3. 使用坐標計算滾動(精確控制像素&…

你寫的 Express 接口 404,可能是被“動態路由”吃掉了

本文首發在我的個人博客:你寫的 Express 接口 404,可能是被“動態路由”吃掉了 前情提要 最近參與公司的一個項目前端 React,后端用的 Express。目前我就做一些功能的新增或者修改。 對于 Express ,本人沒有公司項目實戰經驗&…

【Java面試】你是怎么控制緩存的更新?

🔄 一、數據實時同步失效(強一致性) 原理:數據庫變更后立即失效或更新緩存,保證數據強一致。 實現方式: Cache Aside(旁路緩存): 讀流程:讀緩存 → 未命中則…

react-嵌套路由 二級路由

什么是嵌套路由? 在一級路由中又內嵌了其他路由,這種關系就叫做嵌套路由,嵌套至一級路由內的路由又稱作二級路由 嵌套路由配置 實現步驟 配置二級路由 children嵌套 import Login from "../page/Login/index"; import Home from …

【CMake基礎入門教程】第八課:構建并導出可復用的 CMake 庫(支持 find_package() 查找)

很好!我們進入 第八課:構建并導出可復用的 CMake 庫(支持 find_package() 查找)。 🎯 本課目標 你將掌握: 如何構建一個庫并通過 install() 導出其配置; 如何讓別人在項目中使用 find_package…

Jenkins與Kubernetes深度整合實踐

采用的非jenkins-slave方式 jenkins配置: Jenkins添加k8s master節點的服務器信息 在Jenkins容器內部與k8s master節點設置免費登錄 # docker過濾查詢出運行的Jenkins服務 $ docker ps | grep jenkins# 進入Jenkins容器內部 $ docker exec -it jenkins-server /bi…

GraphQL API-1

簡介 判斷GraphQL方式 判斷一個網站是否使用了GraphQL API,可以通過以下幾種方法: 1. 檢查網絡請求 查看請求端點 GraphQL 通常使用單一端點,常見路徑如: /graphql/api/graphql/gql/query 觀察請求特征 POST 請求為主&…

推薦C++題目練習網站

LeetCode LeetCode是一個全球知名的編程練習平臺,提供大量C題目,涵蓋數據結構、算法、系統設計等。題目難度從簡單到困難,適合不同水平的學習者。平臺支持在線編寫代碼并即時運行測試,提供詳細的題目討論區和官方解答。 Codeforc…

Spring Cloud 微服務(服務注冊與發現原理深度解析)

📌 摘要 在微服務架構中,服務注冊與發現是整個系統運行的基礎核心模塊。它決定了服務如何被定位、調用和管理。 本文將深入講解 Spring Cloud 中 Eureka 的服務注冊與發現機制,從底層原理到源碼分析,再到實際開發中的最佳實踐&a…

【Linux 設備模型框架 kobject 和 kset】

Linux 設備模型框架 kobject 和 kset 一、Linux 設備模型概述二、kobject 與 kset 的核心概念1. kobject2. kset3. 關鍵數據結構 三、kobject 與 kset 的實現源碼四、源碼解析與使用說明1. kset 的創建與初始化2. kobject 的創建與屬性3. sysfs 屬性操作4. 用戶空間訪問示例 五…

一起學前端之HTML------(1)HTML 介紹

HTML 介紹 HTML 即超文本標記語言(HyperText Markup Language),它是構成網頁的基礎技術之一。HTML 借助各種標簽(Tag)對網頁的結構與內容加以描述。下面為你介紹其核心要點: 關鍵特性 標簽結構&#xff…

整體遷移法遷移 Docker 鏡像

docker添加了新的鏡像數據盤,數據盤遷移步驟 使用整體遷移法遷移 Docker 鏡像后,可以在確認遷移成功且新數據盤正常使用后,刪除舊數據目錄來釋放空間1。 # 停止 Docker 服務 sudo systemctl stop docker # 停止 socket 監聽器 sudo systemct…