MySQL索引不起作用

时间:2012-07-12 21:04:50

标签: mysql indexing

我遇到了一个奇怪的MySQL索引问题。我有一张桌子views_video

CREATE TABLE `views_video` (
  `video_id` smallint(5) unsigned NOT NULL,
  `record_date` date NOT NULL,
  `region` char(2) NOT NULL DEFAULT '',
  `views` mediumint(8) unsigned NOT NULL
  PRIMARY KEY (`video_id`,`record_date`,`region`),
  KEY `video_id` (`video_id`)
)

该表包含340万条记录。

我在此查询上运行EXPLAIN

SELECT video_id, views FROM views_video where video_id <= 156

我得到了:

+----+-------------+-------------+-------+------------------+----------+---------+------+--------+-------------+
| id | select_type | table       | type  | possible_keys    | key      | key_len | ref  | rows   | Extra       |
+----+-------------+-------------+-------+------------------+----------+---------+------+--------+-------------+
|  1 | SIMPLE      | views_video | range | PRIMARY,video_id | video_id | 2       | NULL | 587984 | Using where |
+----+-------------+-------------+-------+------------------+----------+---------+------+--------+-------------+

但是当我在此查询上运行EXPLAIN时:

SELECT video_id, views FROM views_video where video_id <= 157

我得到了:

+----+-------------+-------------+------+------------------+------+---------+------+---------+-------------+
| id | select_type | table       | type | possible_keys    | key  | key_len | ref  | rows    | Extra       |
+----+-------------+-------------+------+------------------+------+---------+------+---------+-------------+
|  1 | SIMPLE      | views_video | ALL  | PRIMARY,video_id | NULL | NULL    | NULL | 3412892 | Using where |
+----+-------------+-------------+------+------------------+------+---------+------+---------+-------------+

video_id从1到1034.在156和157之间没有什么特别的。

这里发生了什么?

*更新*

我已将更多数据添加到数据库中。现在video_id是从1到1064.现在该表有3.8M记录。差异变成了114和115。

3 个答案:

答案 0 :(得分:2)

如果您在创建表格后添加/删除了大量数据,那么尝试使用ANALYZE TABLE是值得的。它经常解决很多幻像索引问题,即使在大型表格上它也非常快。

更新:此外,与表中的行数相比,唯一索引值非常低。当单个索引值指向太多行时,MySQL将不使用索引。尝试使用属于主键的另一列进一步限制查询。

答案 1 :(得分:2)

可能是关键人群

运行这些

SELECT (COUNT(1)/20) INTO @FivePctOfData FROM views_video;
SELECT COUNT(1) videpidcount,video_id FROM FROM views_video
WHERE id <= 157 GROUP BY video_id;

当一个密钥达到5%阈值时,查询优化器可能会休假。

你说有340万行。 5%将是170,000。也许在查询优化器的查询生命周期的某个时刻超出了这个数字。

答案 2 :(得分:2)

我猜测有340万条记录,只有1064条可能的条目,你的选择性非常低。 (换句话说,有许多重复项,这使得它作为密钥的用处要小得多。)如果使用密钥更有效,优化器正在进行最佳猜测。你找到了这个决定的门槛。