大家都知道 order by 会导致运行缓慢, 为什么缓慢, 然后怎么解决。 今天来谈谈。
先看一段sql ,
explain select contact_id,department_id,convert(name using gbk) gbk_name from ng_contact where enterprise_id = ‘123’ and department_id = ‘456’ order by contact_level,contact_sort,gbk_name limit 100;
索引:
这里有什么问题呢, 数据量没起来的时候 是没啥问题 毫秒级。
当数据量超过 200万 也就是要在200万数据中 分页 这个SQL 问题就来了。执行很慢, 分页都需要 5-10秒。这样我们肯定是无法忍受的。
那怎么办呢。 我们发现 order gbk_name 此处会扫描所有数据, 罪魁祸首 convert(name using gbk) gbk_name ,
但是 我又需要这个函数怎么办,
我想到的办法是 把此函数计算的 值 放在一个列里面,但是 又不影响其他, 只能考虑 虚拟列了,
我们先试试创建虚拟列:
alter table ng_contact add column gbk_name_index varchar(255) GENERATED ALWAYS AS (convert(name using gbk));
然后创建索引:
alter table ng_contact add index gbk_name_idx(gbk_name_index);
再考虑组合索引:
alter table ng_contact add index gbk_name_idx(enterprise_id, department_id, contact_level,contact_sort, gbk_name_index);
再看看 explain :
接着看看 执行时间 。。是不是飞快:
由于时间有限, 上面 数据为 120万, 仅供参考 ,优化SQL是个漫长而 细腻的事情。