当前位置:网站首页>MySQL索引的B+树到底有多高?
MySQL索引的B+树到底有多高?
2022-08-09 15:33:00 【InfoQ】
一、问题
- h:统称索引的高度;
- h1:聚簇索引的高度;
- h2:二级辅助索引的高度;
- k:中间结点的扇出系数。
二、分析

2.1 索引高度h与页面I/O数的关系
SELECT * FROM USER WHERE id=1- 点查询: 聚族索引:h1 二级索引: 覆盖索引:h2 回表查询:h2+h1
- 范围查询:这种情况相对比较复杂,但跟点查询的原理类似,读者可自行分析;
- 全表查询:B+树的叶子结点是通过链表连接起来的,对于全表查询,需要从头到尾将所有的叶子结点访问一遍。
2.2 索引高度h的理论计算
k^(h-1)k^(h-1)*n三、查看索引真实高度的方法

SELECT b.name, a.name, index_id, type, a.space, a.PAGE_NO
FROM information_schema.INNODB_SYS_INDEXES a,
information_schema.INNODB_SYS_TABLES b
WHERE a.table_id = b.table_id
AND a.space <> 0;
复制代码
hexdump$hexdump -C -s 49216 -n 10 user.ibd
0000c040 00 01 00 00 00 00 00 00 03 2b
复制代码16384*3+64- 通过
information_schema.INNODB_SYS_INDEXES 和 information_schema.INNODB_SYS_TABLES 找到对应索引Root页在ibd文件的页面号PAGE_NO(聚簇索引通常为3,其他索引往上累加);
- 通过
hexdump -C -s 16384*PAGE_NO+64 -n 10 user.ibd ,前两个字节+1即为索引的高度。
四、验证索引的真实高度
CREATE TABLE `user` (
`id` INT(11) NOT NULL AUTO_INCREMENT,
`card_id` INT(11) NOT NULL DEFAULT '0' COMMENT '身份证号',
`name` VARCHAR(32) NOT NULL DEFAULT '' COMMENT '英文名字',
`age` TINYINT(2) UNSIGNED NOT NULL DEFAULT '0' COMMENT '年龄',
`content` VARCHAR(1024) NOT NULL DEFAULT '' COMMENT '附属信息',
`create_time` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`update_time` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '最近更新时间',
PRIMARY KEY (`id`),
UNIQUE KEY `uniq_card_id` (`card_id`),
KEY `idx_name` (`name`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='用户表';
复制代码card_idnamecontent
hexdump -C -s 49216 -n 10 user.ibd && hexdump -C -s 65600 -n 10 user.ibd && hexdump -C -s 81984 -n 10 user.ibdidx_namename五、总结
- 一次查询的页面I/O数跟索引高度h呈正相关,主要分为以下几种情况:
- 点查询: 聚族索引:h1 二级索引: 覆盖索引:h2 回表查询:h2+h1
- 范围查询:这种情况相对比较复杂,但跟点查询的原理类似,读者可自行分析;
- 全表查询:B+树的叶子结点是通过链表连接起来的,对于全表查询,需要从头到尾将所有的叶子结点访问一遍。
- 索引高度通常为2~4层。在高度h=3、主键为int类型、行记录大小为1KB时,可索引的总行数为1170^2*16=2190W。这也是 很多大厂将2000W作为分库分表标准 的原因;
- 查看索引真实高度的方法如下:
- 通过
information_schema.INNODB_SYS_INDEXES 和 information_schema.INNODB_SYS_TABLES 找到对应索引Root页在ibd文件的页面号PAGE_NO(聚簇索引通常为3,其他索引往上累加); - 通过
hexdump -C -s 16384*PAGE_NO+64 -n 10 user.ibd ,前两个字节+1即为索引的高度。
- 索引高度h也跟索引字段的数据类型有关。如果是int或short,扇出系数大,索引效率更好,整个索引看起来属于“矮胖”型;而如果是varchar(32)等,那扇出系数就低了,整个索引看起来属于“瘦高”型,索引效率自然要低些。所以我们在字段选取类型时,其 类型越简单效率越好 。
#聚簇索引(第一个)
hexdump -C -s 49216 -n 10 user.ibd
#第二个索引
hexdump -C -s 65600 -n 10 user.ibd
#第三个索引
hexdump -C -s 81984 -n 10 user.ibd
复制代码边栏推荐
- 巧用Prometheus来扩展kubernetes调度器
- 零基础爬虫regex练习「音乐抓取」
- Heap series_0x09: Example of heap corruption (illegal access + uninitialized + heap handle mismatch)
- resubmit 渐进式防重复提交框架简介
- 4. Using Local Geospatial Data
- 2022年华数杯C题插层熔喷完整解题思路(附代码+详细讲解视频)
- 初始C语言 C生万物
- Why does a four-byte float represent a wider range than an eight-byte long
- 前言:关于作者吴秋生博士与此书简介
- Two ways to find the factorial of n
猜你喜欢

智慧灯杆网关智慧交通应用

设计一个登录小程序(while和getchar实现)

Why does a four-byte float represent a wider range than an eight-byte long

初始C语言(2) C生万物

网络——TCP拥塞控制

uni-app中websocket的使用 断开重连、心跳机制

苹果开发者账号 申请 D-U-N-S 编号
![[Server data recovery] Data recovery case of file system data loss caused by SAN LUN mapping error](/img/fa/a6d9fdc17dd92f68f876df4a6e3ca6.jpg)
[Server data recovery] Data recovery case of file system data loss caused by SAN LUN mapping error

推荐一些面向 Web 开发者的杀手级网站

BETA:一个用于计算药物靶标预测的综合基准
随机推荐
C语言的常量和操作符
初识C语言,了解一下C语言轮廓
推荐一些面向 Web 开发者的杀手级网站
Redis Cache Expiration and Retirement Policy
【Web渗透】信息收集篇——Google搜索引擎(二)
三.两数交换 空指针 && 野指针 解引用问题
#yyds干货盘点# 面试必刷TOP101:删除有序链表中重复的元素-II
微服务框架笔记(1)
想通这点,治好 AI 打工人的精神内耗
C语言三子棋详解
5G NR Paging 寻呼
4. Using Local Geospatial Data
2022年8月9日:用C#生成.NET应用程序--使用 Visual Studio Code 调试器,以交互方式调试 .NET 应用(不会,失败)
No need to pay for the 688 Apple developer account, xcode13 packaged and exported ipa, and provided others for internal testing
五.初始指针
yolov5训练并生成rknn模型以及3588平台部署
SQL抖音面试题:送你一个万能模板,要吗?(重点、每个用户每月连续登录的最大天数)
std::uniform_real_distribution的一个bug引发的服务器崩溃
第五章:可视化地理空间数据
Smart Light Pole Gateway Smart Transportation Application