【问题标题】:Using filesort in simple query在简单查询中使用文件排序
【发布时间】:2013-07-18 14:34:37
【问题描述】:

我有一个非常简单的表格:

CREATE TABLE `navigation` (
  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `parent_id` int(11) unsigned DEFAULT NULL,
  `title` varchar(255) NOT NULL COMMENT 'Название ссылки',
  `priority` tinyint(3) NOT NULL COMMENT 'Параметр сортировки'
  PRIMARY KEY (`id`)
) ENGINE=InnoDB;

只有 41 行。我也有非常简单的查询:

mysql> EXPLAIN SELECT t.id, t.parent_id, t.title, t.priority FROM navigation t ORDER BY t.priority ASC;
+----+-------------+-------+------+---------------+------+---------+------+------+----------------+
| id | select_type | table | type | possible_keys | key  | key_len | ref  | rows | Extra          |
+----+-------------+-------+------+---------------+------+---------+------+------+----------------+
|  1 | SIMPLE      | t     | ALL  | NULL          | NULL | NULL    | NULL |   41 | Using filesort |
+----+-------------+-------+------+---------------+------+---------+------+------+----------------+
1 row in set (0.00 sec)

如何避免使用filesort?还是不可能? 我已经阅读了很多关于 SO 的主题,但无法理解正确的答案。 谢谢。

【问题讨论】:

  • 只有 41 行,你为什么在乎?
  • 因为我现在只有 41 行,但在生产中有很多行。并且生产服务器(MySQL)也有使用文件排序。

标签: mysql sql explain


【解决方案1】:

如何避免使用文件排序?还是不可能?我已经阅读了很多关于 SO 的主题,但无法理解正确的答案。

您需要在priority 列上建立索引:

ALTER TABLE navigation ADD INDEX (priority);

然而,MySQL 可能会计算出使用这样的索引对结果进行排序最终会比filesort 更昂贵(因为前者将涉及顺序读取索引文件以执行随机 I/O到表中,而后者将涉及顺序读取表并对结果执行内存排序)。您可以使用index hint 覆盖此评估:

SELECT   t.id, t.parent_id, t.title, t.priority
FROM     navigation t FORCE INDEX FOR ORDER BY (priority)
ORDER BY t.priority ASC;

covering index 将完全避免读取表的需要,因此只需按顺序遍历索引文件即可立即返回结果;因此,查询优化器可能会在没有进一步提示的情况下选择它:

ALTER TABLE navigation ADD INDEX(priority, id, parent_id, title);

哪种方法适合您将取决于您的应用程序的要求,但请记住 Knuth 的格言:“过早的优化是万恶之源

【讨论】:

    【解决方案2】:

    为了避免文件排序,大多数时候您应该添加索引。在您的情况下,这意味着 priority 列上的索引。你可以这样做:

    ALTER TABLE `navigation` ADD INDEX (`priority`);
    

    请注意,即使使用此索引,仍然可能使用文件排序,因为这实际上可能比使用索引更快。即使定义了索引,也可能是 41 行。

    【讨论】:

      【解决方案3】:

      根据this blog post filesort 每次您对未索引的列进行排序时都会发生。它与文件系统中发生的实际排序无关。 使用Erik's answer 中的描述,您应该摆脱它。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-02-26
        • 1970-01-01
        • 1970-01-01
        • 2014-01-08
        • 1970-01-01
        • 2013-09-15
        相关资源
        最近更新 更多