MySQL没有有效地使用索引进行ORDER BY查询

时间:2009-09-07 08:51:14

标签: mysql indexing

我有一个简单的Message表,有两个索引:

mysql> show keys from Message;
+---------+------------+-----------+--------------+----------------+-----------+-------------+----------+--------+------+------------+---------+
| Table   | Non_unique | Key_name  | Seq_in_index | Column_name    | Collation | Cardinality | Sub_part | Packed | Null | Index_type | Comment |
+---------+------------+-----------+--------------+----------------+-----------+-------------+----------+--------+------+------------+---------+
| Message |          0 | PRIMARY   |            1 | id             | A         |     5643295 |     NULL | NULL   |      | BTREE      |         |
| Message |          1 | timestamp |            1 | startTimestamp | A         |     5643295 |     NULL | NULL   |      | BTREE      |         |
+---------+------------+-----------+--------------+----------------+-----------+-------------+----------+--------+------+------------+---------+

通过查询发出订单时,会检查大量的行:

mysql> explain SELECT * from Message ORDER BY startTimestamp LIMIT 0,20;
+----+-------------+---------+-------+---------------+-----------+---------+------+---------+-------+
| id | select_type | table   | type  | possible_keys | key       | key_len | ref  | rows    | Extra |
+----+-------------+---------+-------+---------------+-----------+---------+------+---------+-------+
|  1 | SIMPLE      | Message | index | NULL          | timestamp | 8       | NULL | 5643592 |       |
+----+-------------+---------+-------+---------------+-----------+---------+------+---------+-------+

总行数为:

mysql> select count(*) from Message;
+----------+
| count(*) |
+----------+
|  5837363 |
+----------+

此查询涉及96.7%的行。索引是BTREE,所以据我所知它应该只是抽出前20行并返回它们。就目前而言,它使用索引来访问几乎所有表的行,这可能比全表扫描慢。

我错误地假设它应该只使用索引选择前20行并返回它们?

MySQL服务器版本为5.0.45,表格类型为InnoDB

2 个答案:

答案 0 :(得分:2)

  

使用EXPLAIN SELECT ... ORDER BY,你   可以检查MySQL是否可以使用   用于解析查询的索引。它   如果你看到使用filesort,则不能   Extra列。

正在使用索引..

答案 1 :(得分:2)

在EXPLAIN中,MySQL估计扫描的行数为5643592,但它使用的是正确的索引(按列排序:timestamp),并且限制为20行,所以不要担心它正在做正确的事情并将停止为很快就会发送20行。你能给我们一个查询执行时间吗?