最准确的方法是查询 INFORMATION_SCHEMA.TABLES 表,其中 INDEX_LENGTH 字段表示索引实际磁盘占用字节数,DATA_LENGTH 表示数据大小,二者之和即表总空间占用,单位需除以1024²换算为MB。
直接查 INFORMATION_SCHEMA 表最准
phpmyadmin 本身不提供索引空间的可视化统计,但底层 mysql 的 information_schema.statistics 和 information_schema.tables 能间接反映索引大小。真正能查到索引实际磁盘占用的,是 information_schema.tables 中的 data_length 和 index_length 字段——后者就是当前表所有索引加起来占了多少字节。
执行这条 SQL 即可(把 your_database 和 your_table 换成实际值):
SELECT TABLE_NAME AS `表名`, ROUND(INDEX_LENGTH / 1024 / 1024, 2) AS `索引大小(MB)`, ROUND(DATA_LENGTH / 1024 / 1024, 2) AS `数据大小(MB)` FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA = 'your_database' AND TABLE_NAME = 'your_table';
注意:INDEX_LENGTH 是估算值,InnoDB 表可能略低于真实物理占用(因页内碎片、未合并的 B+ 树节点等),但对日常判断“哪个表索引膨胀严重”完全够用。
SHOW INDEX 只显示结构,不显示大小
很多人误以为 SHOW INDEX FROM your_table 能看到索引体积,其实它只返回字段名、类型、是否唯一、序列号等元信息,没有任何字节或页数相关字段。它适合确认索引是否存在、顺序是否合理,但不能用于容量分析。
- 如果你在 phpMyAdmin 的“结构”页点“索引”,背后调的就是
SHOW INDEX,别指望那里看到 MB 数字 - 复合索引的字段顺序、前缀长度会影响实际存储开销,但这些细节也得靠人工估算,
SHOW INDEX不会帮你算
InnoDB 表的 INDEX_LENGTH 包含聚簇索引吗?
包含,但要分清逻辑和物理:InnoDB 的主键即聚簇索引,它的数据页同时存了行记录和主键结构,所以 INDEX_LENGTH 里不单独计入主键索引的数据页体积,只计入二级索引(非主键索引)的 B+ 树页。而 DATA_LENGTH 已包含聚簇索引的叶子页内容。
立即学习“PHP免费学习笔记(深入)”;
换句话说:
-
DATA_LENGTH≈ 聚簇索引叶子页 + 行记录总大小 -
INDEX_LENGTH≈ 所有二级索引的内部节点 + 叶子节点总大小 - 所以
DATA_LENGTH + INDEX_LENGTH≈ 整个表在 ibd 文件里的大致占比(不含系统表空间开销)
为什么有时候 INDEX_LENGTH 是 0?
常见于 MyISAM 表或刚创建还没插入数据的 InnoDB 表。但更隐蔽的情况是:MySQL 在某些版本(如 5.7 早期)中,如果表被 ANALYZE TABLE 后未触发统计更新,INDEX_LENGTH 可能滞后。此时可手动刷新:
ANALYZE TABLE your_table;
然后立刻重查 INFORMATION_SCHEMA.TABLES。另外,视图、临时表、分区表的子分区也可能返回 0,需确认 TABLE_TYPE 是 BASE TABLE 且引擎为 InnoDB 或 MyISAM。
真正容易被忽略的是:索引大小不是静态值,INSERT/UPDATE/DELETE 频繁后,B+ 树分裂、页合并、删除标记清理都会让 INDEX_LENGTH 波动——别拿一次查询结果当长期容量依据。



















