手机扫一扫访问本页内容

微信扫描点右上角"···"分享到好友或朋友圈

关闭
微信扫一扫可打开小程序

微信长按图片或搜“分享录”可打开小程序

关闭
MySQL,经验 , , ,

MySQL创建联合索引报key长度超3072 bytes的[42000][1071]错误

问题时这样的,我在建表时加了联合索引结果报key长度超过3072个字节了,如下图。

[42000][1071] Specified key was too long; max key length is 3072 bytes

先说解决方案:1.调整索引字段,包括修改字段长度、更换字段;2.使用前缀索引

在MySQL 5.6以及以前的版本,InnoDB引擎默认索引长度不能超过767 bytes,在MySQL 5.5以后支持4个字节的utf8mb4(mb4全称maximun of 4 bytes per multibyte character),也就是说当CHARSET=utf8mb4时varchar最大只能是varchar(191),因为192×4=768大于767了。

可以通过开启innodb_large_prefix让InnoDB引擎默认索引长度达到3072 bytes,在MySQL 5.6默认innodb_large_prefix=OFF,可以通过设置innodb_large_prefix=ON、innodb_file_format=barracuda、innodb_file_per_table=true 且Innodb表的存储格式(row format)为 DYNAMIC 或 COMPRESSED让索引长度达到3072 bytes。

#MySQL 5.6以及以前的版本可执行
set global innodb_large_prefix=1;
set global innodb_file_format=BARRACUDA;

MySQL 5.7默认innodb_large_prefix=ON,到MySQL 8.0以后直接remove了innodb_large_prefix、innodb_file_format等变量,row format为DYNAMIC或COMPRESSED让索引长度达到3072 bytes,REDUNDANT和COMPACT只有767 bytes,MySQL 8.0默认innodb_default_row_format=DYNAMIC,所以高版本不用动,前提一定要是InnoDB引擎,MyISAM引擎默认是1000 bytes,NDB则不支持。

为什么是767和3072?网上查资料说,767是历史问题,char最大是255,以前设计者以为一个长度255的索引就够用了,以前UTF8最大支持3个字节,256×3-1=767;InnoDB一个page的默认大小是16k,由于是Btree组织,要求叶子节点上一个page至少要包含两条记录,所以一个记录最多不能超过8k,又由于InnoDB的聚簇索引结构,一个二级索引要包含主键索引,因此每个单个索引不能超过4k (极端情况,primay-key和某个二级索引都达到这个限制),由于需要预留和辅助空间,减掉后不能超过3500,取个“整数”即1024bytes3=3072bytes。

接着说下解决方案,InnoDB引擎默认索引长度最大只能是3072 bytes,对此我想到这两个方案:1.调整索引字段,包括修改字段长度、更换字段;2.使用前缀索引。其中修改字段长度可能会报“[22001][1406] Data truncation: Data too long for column ‘xxx’ at row N”错。 前缀索引就是用该列的前面部分字符来创建索引,官方给的例子如下:

CREATE INDEX part_of_name ON customer (name(10));

创建前缀索引前我们可以先比较重复率 :

select 1.0*count(distinct 字段名)/count(*) from 表名;
select 1.0*count(distinct left(字段名, 1))/count(*) from 表名;
select 1.0*count(distinct left(字段名, 2))/count(*) from 表名;
select 1.0*count(distinct left(字段名, 3))/count(*) from 表名;
select 1.0*count(distinct left(字段名, 4))/count(*) from 表名;
...

最后取结果最接近或等于1的那个,然后添加前缀索引“alter table 表名 add key(字段名(数字));”,其中left函数会返回具有指定长度的字符串的左边部分(LEFT(str, length))。


展开阅读全文


上一篇:

下一篇:

服务器又要到期了鼓励一下吧
您还可以访问本站的小程序、公众号等所有端,或者下载APP, 在小程序、APP上可以评论文章以及保存图片还有在线客服哦,如您有任何疑问或建议可向作者提出意见反馈
扫码打开小程序可评论文章保存图片,在“我的”有实时在线客服哦,看效果?
关注我的公众号为您分享各类有用信息
分享录多端跨平台系统