mysql IN子句不使用可能的键

时间:2013-01-22 18:42:41

标签: mysql query-optimization sql-execution-plan

我有一个相当简单的mysql查询,它包含一些内连接,然后是一个where子句。我已经为连接中使用的所有列以及主键创建了索引。我还有一个包含IN运算符的where子句。当只有5个或更少的id传递到IN子句时,查询优化器使用我的一个索引在合理的时间内运行查询。当我使用说明时,我看到类型是范围,键是主要的。我的问题是,如果我在IN子句中使用超过5个ID,优化器将忽略所有可用索引,并且查询运行速度极慢。当我使用说明时,我看到类型是ALL,键是NULL。

有人可以请说明这里发生的事情以及如何解决这个问题。

由于

3 个答案:

答案 0 :(得分:0)

无论表上的“主键”索引如何优化JOIN,您还应该有一个基于您应用WHERE的常用条件的索引。您的查询列需要更多信息,但您应该在WHERE标准TOO上有索引。

答案 1 :(得分:0)

您也可以尝试使用Mysql Index Hints。它允许您指定在查询执行期间应使用哪个索引。

示例:

 SELECT * FROM table1 USE INDEX (col1_index,col2_index)
  WHERE col1=1 AND col2=2 AND col3=3;

-

SELECT * FROM table1 IGNORE INDEX (col3_index)
  WHERE col1=1 AND col2=2 AND col3=3;

更多信息: Mysql Index Hints

答案 2 :(得分:0)

在检查我遇到的类似问题时找到了这个。我认为我的发现可能会帮助其他任何有类似问题的人。

我有一个大约30行的MyISAM表(包含搜索类似单词的常见拼写错误,其中可能的原始拼写错误和替代单词可能都是有效的拼写,表格的大小会慢慢增加)。然而,对我来说,如果IN子句中有4个项目使用了索引,但是当IN子句中有5个时,则忽略索引(注意我没有尝试替代词,因此IN子句中的实际单个项目可能是一个因素)。与OP类似,但字数不同。

使用索引不起作用,索引仍会被忽略。 强制索引确实有效,但我宁愿避免指定索引(以防万一有人删除索引)。

对于某些测试,我使用额外的1000个随机唯一行填充表格,查询将使用相关索引,即使在IN子句中有80个项目。

所以似乎MySQL决定是否使用基于IN子句中项目数量的索引与表格中的行数相比(尽管可能还有一些其他因素)。