Mysql指定索引强制使用某个索引优化查询

简介:MySQL指定使用某个索引,MySQL强制使用某个索引,MySQL禁用某个索引

在使用MySQL进行查询时,我们经常会遇到SQL执行没有按照我们预想的那样去使用某个索引优化查询,那怎么解决这个问题呢?

对于这个问题,MySQL给我们准备了三个方法,这三个方法可以帮助我们让SQL执行按照我们预想的那样去选择索引。今天我们就针对这三个方法分别来说说吧!

  • use index:在你查询语句表名的后面,添加use index来提供你希望mysql去参考的索引列表,就可以让mysql不再考虑其他可用的索引。如:select * from table use index(name,age);
  • IGNORE INDEX: 提示会禁止查询优化器使用指定的索引。在具有多个索引的查询时,可以用来指定不需要优化器使用的那个索引,还可以在删除不必要的索引之前在查询中禁止使用该索引。如:select * from table ignore index(name,age);
  • force index:强制mysql使用一个特定的索引。一般情况下mysql会根据统计信息选择正确的索引,但是当查询优化器选择了错误的索引或根本没有使用索引的时候,这个提示将非常有用。

注意:use/ignore/force index(index) 括号里的index是索引名,而不是列名。而且后面必须要加上where条件

现在我们已经了解了MySQL提供的指定索引的三个方法,接下来我们就针对这三个方法来实验一下具体的操作及结果吧!

准备表

create table `test`(
`id` int UNSIGNED primary key auto_increment,
`a` int(11) NOT NULL DEFAULT '0' COMMENT '测试字段a',
`b` int UNSIGNED not null default 0 comment '测试字段b',
`c` int UNSIGNED not null default 0 comment '测试字段c',
index a_index(`a`),
index b_index(`b`),
index c_index(`c`)
)engine=innodb default charset utf8 comment '测试表';

我们可以添加一些测试数据,将下面的SQL重复执行100遍

insert into test(a,b,c) values (1,1,1),(2,2,2),(3,3,3),(4,4,4),(5,5,5),(6,6,6),(7,7,7),(8,8,8),(9,9,9),(11,11,11);

有了数据后,我们再来看看具体的测试结果吧

1
use index()

在没有指定索引的情况下,SQL会如何执行呢?

从上面的结果可以看出这种方式没有使用索引,会导致全表扫描

2
use index(a)

只指定一个索引时SQL是否走索引呢?使用的索引是哪一个?

由上面的SQL分析可以看出,where条件中有索引字段而【use index】指定了其他索引时,索引失效。但是【use index】指定的索引的字段存在where条件中,指定的索引才会生效,还会导致全表扫描。

3
use index(a) use use index(b)

上面的SQL同时指定了两个索引,SQL又会怎么去执行呢?

由上面的SQL分析可以看出,使用【use index】多次指定索引和一次指定索引效果一样,主要还是要看指定的索引关联的字段是否存在where条件中,存在索引生效,否则不生效,还会导致全表扫描。

4
use index(a) ignore index(a) use use index(b)

同时指定两个索引后又禁用了其中一个索引,这样的SQL又会如何去执行呢?

由上面的SQL分析结果:从前两个SQL可以看出,不管【ignore index】的位置在哪里,只要设置了禁用的索引,那这个索引就会失效,如果禁用的索引关联的字段与where条件中索引字段相同,即使指定了其他所有,所有索引都将失效,从而导致全表扫描。这一点和上面第三个测试结果一样

5
force index()

force index】是强制使用索引

分析结果如下:

从第一条SQL可以看出【force index】必须设置索引名,否则就会报错。

从第二条SQL可以看出,使用了【force index】就不能再使用【use index】指定其他索引,否则会报错。

如果【force index】强制使用的索引关联的字段不在where条件中,此时【force index】强制指定的索引失效,还会导致全表扫描。

如果【force index】强制索引关联的字段在where条件中,此时就会使用强制设置的索引。如下图所示:

总结一下:

1,【use index】没有指定索引会导致全表扫描,指定的索引关联的字段不在where条件中依然不使用索引,导致全表扫描。所以指定索引时注意索引关联的字段是否在where条件中。

2,【ignore index】必须设置索引名,否则会报错。禁用的索引一定导致索引失效,即使使用【use index】重新指定该索引也无效

3,【force index】必须指定索引名。强制指定的索引关联的字段不在where条件中,所有索引都将失效。而且不能与【use index】同时使用

有遗漏或者不对的可以在我的公众号留言哦

编程经验共享公众号二维码

编程经验共享公众号二维码
更多内容关注公众号
Copyright © 2021 编程经验共享 赣ICP备2021010401号-1