一个MYSQL语句优化的问题

A是数据表共有30万条数据,b,c,d 是字段,我给b和c,d分别加了index索引

执行

EXPLAIN SELECT * FROM A WHERE b=0 AND c='hk' ORDER BY d DESC LIMIT 1,30

用时41.7ms(实际体验很慢)

结果:

select_type table type possible_key key key_len ref rows Extra
SIMPLE A index_merge b,c b,c 6,4 NULL 55577 Using intersect(region,cheat); Using where; Using filesort

请问我该怎么优化

阅读 2.8k
4 个回答

你的type是index_merge类型的,意味着你的sql是先用b的索引查找b=0的数据,然后在用c的索引查找c='hk'的的项,然后取这两个集合的交集。虽然你在d上面也建了索引,但是explain的结果告诉你排序的时候并没有用得到d的索引,而是扫描所有的结果集。
因此,我的建议是建立联合索引(b.c.d)。建立联合索引的有一个向左原则,把最常用的那个字段放到最左边

字段B和C建立一个联合索引,字段D不需要建索引。

index_merge说明用到了多个索引,像你这种多个条件一起用的话肯定首选复合索引了,
使用“=”精确筛选的字段放前面,范围/排序字段放后面,然后使用“=”的字段也要根据筛选率选择好顺序,
比如表中b的值有10个,而c有1000个,就把c放在复合索引最前端,索引顺序就是(c,b,d),反之就把b放前面。

另外,这位兄台你这个41.7ms是生成执行计划的时间,并不是执行sql的时间,explain只是让mysql生成你这条sql的执行计划,并不会真正执行。

自己搞定了,删掉了b或c其中一个索引,就可以了

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题