Mysql索引长度的计算

索引长度限制

MySQL Innodb 对于索引长度的限制为 767 字节,并且UTF8mb4字符集是4字节字符集,则 767字节 / 4字节每字符 = 191字符(默认索引最大长度),所以在varchar(255)或char(255) 类型字段上创建索引会失败,提示最大索引长度为767字节

长度计算

定长类型:int占四个字节、date占三个字节、char(n)占n个字符。

对于varchar(n),则有n个字符+两个字节。(MySQL需要1 ~ 2个字节来表示字符串的长度。具体来说,如果字符串占用的字节数在 0 ~255 之间,需1个字节来表示,如果大于 255 个字节,则需2个字节来表示)

不同的字符集,一个字符占用的字节数不同

latin1编码:一个字符占用一个字节。

gbk编码的:一个字符占用两个字节。

utf8编码的:一个字符占用三个字节。

针对索引长度 char()、varchar()索引长度的计算公式:

(Character Set:utf8mb4=4,utf8=3,gbk=2,latin1=1) * 列长度 + 1(允许null) + 2(变长列)

求证

1.查看表结构

show full columns from [table]

2.增加索引

ALTER TABLE `mail_receive_log` ADD INDEX `idx_channel_uid` (channel_uid);

3.查看索引长度

64*4+1+2=259

 案例

1.线上发现一个慢sql

explain  select * from mail_receive_log r
where r.to='liqinad@qq.com' and r.created_at>'2022-04-01'

2.查看执行计划

全表扫描没命中索引

 3.查看现在存在索引 是否有合适索引

2550*3+1+2=7 653 超过索引长度了

 4.没有合适索引准备在to建立索引查看表结构

5.分析准备线上数据

奇怪的数据是json 怀疑是批量发送存储的json数组。

6.定位到代码调用发现是查询的一个config文件传递的email进去查询

 7.查看config表的email最大长度

 8.建立索引

42*3+2+1=129没有超出限制 大于42位条件查询走全表扫描

ALTER TABLE `mail_receive_log` ADD INDEX `ix_to_created_at` (`to`(42),created_at);

9.优化后执行计划

length=133 是因为 129+时间长度的3个字节=133

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值