聊聊InnoDB的数据页,和B+树的关系是什么?
1 个回答
你爱你的玫瑰是因为你在你的玫瑰上花了太多的时间!柳若雪在 **InnoDB 存储引擎** 中,**数据页(Page)是数据存储的基本单位**,而 **B+ 树是 InnoDB 用于索引组织的数据结构**。两者的结合,使得 **MySQL 能够高效地管理和检索数据**。 ## **1. InnoDB 的数据页** ### **1.1 什么是数据页?** - **数据页(Page)是 InnoDB 存储数据的基本单位**,每个数据页大小通常为 **16KB**(可通过 `innodb_page_size` 调整)。 - **MySQL 读写数据的最小单位是 16KB**,即: - **一次磁盘读取最少 16KB**(即使查询一行)。 - **数据修改后,最小的刷盘单位也是 16KB**。 ### **1.2 数据页的结构** 每个 **数据页(16KB)** 包含 **多个数据行**,存储格式如下: ``` +--------------------+ | 页头(Page Header)| 组织管理信息 +--------------------+ | 记录目录 | 用于快速定位数据 +--------------------+ | 用户数据 | 实际存储的行记录 +--------------------+ | 页目录 | 记录行数据的偏移量 +--------------------+ | 页尾(Page Trailer)| 用于校验完整性 +--------------------+ ``` ✅ **每个数据页存储多个行数据**,但如果一行数据 **过大**,可能会**溢出到其他页(LOB 大对象存储)。** ## **2. B+ 树与数据页的关系** **B+ 树(B+ Tree)是 InnoDB 组织索引的方式**,索引节点和数据页直接相关: 1. **B+ 树的每个节点对应一个数据页**。 2. **B+ 树的非叶子节点存储索引(主键 + 指向子节点的指针)**。 3. **B+ 树的叶子节点存储实际数据**,叶子节点之间通过**双向链表连接**。 ### **2.1 聚簇索引(Clustered Index)** 在 **InnoDB** 中,**表的数据是按照主键顺序存储的**,因此 **数据页的组织方式** 直接由 **B+ 树的结构** 决定。 #### **B+ 树结构** ``` [100 200 300] ← 非叶子节点(索引) / | \ [1-99] [100-199] [200-299] ← 叶子节点(数据页) ``` - **非叶子节点存储主键和指向子节点的指针**。 - **叶子节点存储数据页,每个页 16KB,包含多行数据**。 ✅ **查找数据时,从根节点开始,逐层遍历,最终到达叶子节点的数据页。** ### **2.2 B+ 树的层级与数据页** #### **假设数据页大小 16KB,每行数据 1KB** - **一个数据页 ≈ 16 行数据**。 - **一个非叶子节点存储 100 个索引项**。 - **总数据量 100 万行,B+ 树的层级如下**: - **第 1 层(根节点)**:存储 **100** 个索引项。 - **第 2 层(中间节点)**:存储 **10,000** 个索引项。 - **第 3 层(叶子节点)**:实际存储数据页,共 100,000 页。 ✅ **一般 3~4 层的 B+ 树就能索引百万级数据,查询性能高效。** ## **3. InnoDB 如何利用 B+ 树与数据页?** ### **3.1 插入数据** 1. **找到合适的叶子节点(数据页)**: - 通过 **B+ 树索引** 定位 **主键范围对应的数据页**。 2. **插入数据** - 如果 **当前数据页有空位**,直接插入。 - 如果 **数据页满了**,则 **触发页分裂**: - 创建新数据页,将部分数据迁移,更新 B+ 树索引。 ✅ **页分裂会增加 B+ 树的高度,导致查询效率下降,影响写入性能。** ### **3.2 查询数据** 1. **从 B+ 树根节点开始,按主键范围遍历索引**。 2. **找到目标叶子节点,访问数据页,读取数据行**。 3. **如果是范围查询(BETWEEN、ORDER BY)**,则利用 **叶子节点的双向链表** 顺序扫描。 ✅ **B+ 树保证了查询只需访问很少的磁盘页,提高查询效率。** ### **3.3 删除数据** 1. **找到数据页,删除行数据**。 2. **如果数据页剩余数据过少,可能触发页合并**: - 将数据合并到相邻页,减少磁盘空间浪费。 ✅ **页合并可以减少 B+ 树的高度,提高查询性能。** ## **4. 总结** | **概念** | **作用** | |----------|---------| | **数据页(Page)** | 存储数据的最小单位(默认 16KB),一次 IO 读取最小 16KB | | **B+ 树** | 用于索引数据页,非叶子节点存储索引,叶子节点存储实际数据 | | **聚簇索引(Clustered Index)** | 表数据按照主键存储,B+ 树叶子节点就是数据页 | | **页分裂 & 页合并** | 页满时创建新页,数据删除后可能合并,影响查询和写入性能 |发布于 2025-03-12 18:45 •IP属地 山西举报评论收藏
公众号进入网站体验更佳

