Mysql 页分裂页合并

时间:2025-03-21 08:39:46

InooDB的文件格式,ibd利用主键索引到具体数据,数据都在叶节点上,frm就是一些数据库的元信息了。

重点看看ibd文件,这个文件由多个段组成,每个段和一个索引相关。

文件的结构是不会随着数据行的删除而变化的,但段则会跟着构成它的更小一级单位——区的变化而变化。页则是区的下一级构成单位,默认体积为16KB。

每个页(逻辑上讲即叶子节点)是包含了2-N行数据,根据主键排列

InnoDB不是按行的来操作的,它可操作的最小粒度是页,页加载进内存后才会通过扫描页来获取行/记录。

页合并

当你删了一行记录时,实际上记录并没有被物理删除,记录被标记(flaged)为删除并且它的空间变得允许被其他记录声明使用。

当页中删除的记录达到MERGE_THRESHOLD(默认页体积的50%),InnoDB会开始寻找最靠近的页(前或后)看看是否可以将两个页合并以优化空间使用。

页合并发生在删除更新操作中,关联到当前页的相邻页。如果页合并成功,在INFOMATION_SCHEMA.INNODB_METRICS中的index_page_merge_successful将会增加

页分裂

如果一个数据应该被插入第10页,但是10页满了,11页也满了,那怎么办?

直接把第10页分裂成两个,页分裂会发生在插入或更新,并且造成页的错位(dislocation,落入不同的区)

InnoDB用INFORMATION_SCHEMA.INNODB_METRICS表来跟踪页的分裂数。可以查看其中的index_page_splitsindex_page_reorg_attempts/successful统计。

一旦创建分裂的页,唯一将原先顺序恢复的办法就是新分裂出来的页因为低于合并阈值(merge threshold)被删掉。这时候InnoDB用页合并将数据合并回来。

另一种方式就是用OPTIMIZE重新整理表。这可能是个很重量级和耗时的过程,但可能是唯一将大量分布在不同区的页理顺的方法。


要注意的是在合并和分裂的过程中会加锁