MySQL没有使用索引

时间:2009-10-24 15:38:00

标签: sql mysql optimization

我刚刚启用了慢速日志(+没有使用索引),并且我为同一类查询获得了数百个条目(仅user更改)

SELECT id
     , name 
  FROM `all` 
 WHERE id NOT IN(SELECT id 
                   FROM `picks` 
                  WHERE user=999) 
ORDER BY name ASC;

EXPLAIN给出:

+----+--------------------+-------------------+-------+------------------+--------+---------+------------+------+------------------------------------------+
| id | select_type        | table             | type  | possible_keys    | key    | key_len | ref        | rows | Extra                                    |
+----+--------------------+-------------------+-------+------------------+--------+---------+------------+------+------------------------------------------+
|  1 | PRIMARY            | all               | index | NULL             | name   | 156     | NULL       |  209 | Using where; Using index; Using filesort | 
|  2 | DEPENDENT SUBQUERY | picks             | ref   | user,user_2,pick | user_2 | 8       | const,func |    1 | Using where; Using index                 | 
+----+--------------------+-------------------+-------+------------------+--------+---------+------------+------+------------------------------------------+

有关如何优化此查询的任何想法?我已尝试在不同的领域使用一堆不同的索引,但没有。

3 个答案:

答案 0 :(得分:0)

“不在”和“存在”总是糟糕的表现选择。可能是左边加入cheking“NULL”会更好试试。

答案 1 :(得分:0)

我不一定同意'不在'和'存在'总是表现不佳,但是,它可能就是这种情况。

您可以使用更简单的查询来获取结果:

SELECT id
     , name 
  FROM `all`
     , 'picks'
 WHERE all.id = picks.id
   AND picks.user <> 999 
ORDER BY name ASC;

答案 2 :(得分:0)

这可能是编写查询的最佳方式。从all中选择所有内容,然后尝试查找共享相同picksiduser的{​​{1}}匹配行。如果此行不存在,999将为picks.id,因为它使用左外连接。然后,您可以过滤结果以仅返回那些行。

NULL