总结
对于比较长的字符串字段可以使用前缀索引。使用前缀索引,定义好长度,就可以做到既节省空间,又不用额外增加太多的查询成本。
如何确定应该使用多长的前缀?
在建立索引时关注的是区分度,区分度越高越好。因为区分度越高,意味着重复的键值越少。因此,我们可以通过统计索引上有多少个不同的值来判断要使用多长的前缀。
首先,你可以使用下面这个语句,算出这个列上有多少个不同的值:
select count(distinct email) as L from SUser;
然后,依次选取不同长度的前缀来看这个值,比如我们要看一下 4~7 个字符的前缀索引,可以用这个语句:
select
count(distinct left(email,4))as L4,
count(distinct left(email,5))as L5,
count(distinct left(email,6))as L6,
count(distinct left(email,7))as L7,
from SUser;
使用前缀索引很可能会损失区分度,所以你需要预先设定一个可以接受的损失比例,比如 5%。然后,在返回的 L4~L7 中,找出不小于 L * 95% 的值,假设这里 L6、L7 都满足,你就可以选择前缀长度为 6。
前缀索引对覆盖索引的影响
使用前缀索引就用不上覆盖索引对查询性能的优化了
字符串字段创建索引的场景
可以使用的方式有:
-
直接创建完整索引,这样可能比较占用空间;
-
创建前缀索引,节省空间,但会增加查询扫描次数,并且不能使用覆盖索引;
-
倒序存储,再创建前缀索引,用于绕过字符串本身前缀的区分度不够的问题;
-
创建 hash 字段索引,查询性能稳定,有额外的存储和计算消耗,跟第三种方式一样,都不支持范围扫描。