用于大表的TIMESTAMP列的比较

时间:2016-03-31 14:13:02

标签: mysql innodb

我有一个MySQL(InnoDB)表,其中有大量行(几百万)。我这样做的是查询:

SELECT  SQL_CALC_FOUND_ROWS `a` 
FROM  `logs`  
WHERE  `connect_timestamp`  > 10000 
ORDER  BY  `connect_timestamp`  DESC 
LIMIT 1

我在列中添加了一个普通的索引,但像这样的查询最多需要20秒,还有更好的方法吗?

2 个答案:

答案 0 :(得分:1)

根据spencer7593和Martin的评论进行编辑:

简单的count + select查询可能比一个SQL_CALC_FOUND_ROWS快得多。看到: Which is fastest? SELECT SQL_CALC_FOUND_ROWS FROM `table`, or SELECT COUNT(*)

我建议您同时运行原始查询:

SELECT  count(*)
FROM  `logs`  
WHERE  `connect_timestamp`  > 10000

加:

SELECT  `a`
FROM  `logs`  
WHERE  `connect_timestamp`  > 10000 
ORDER  BY  `connect_timestamp`  DESC 
LIMIT 1

最好甚至运行所有使用EXPLAIN来测量(并添加)运行时并查看差异,您还可以添加SQL_NO_CACHE来模拟第一次运行。见:https://www.percona.com/blog/2007/08/28/to-sql_calc_found_rows-or-not-to-sql_calc_found_rows/

如果这根本没有帮助,我建议调查以下内容:

你可以尝试的事情:

  • 索引用于搜索的列(您似乎已经这样做了)
  • 查看经常执行的特定查询。
  • 如果服务器有内存,请尝试缓存特定的表。
  • 也像Martin在评论中所说的那样,将EXPLAIN放在查询前面,以查看查询的哪一部分一直在占用。也许你可以改变它。

这些是我能想到的。

答案 1 :(得分:0)

INDEX(connect_timestamp, a)

这将是一个"覆盖"索引,从而加快了SQL_CALC_FOUND_ROWS以及SELECT ... LIMIT 1

它必须从索引的末尾一直扫描回10000.那是多少行?

如果connect_timestamp是某些类型的CHAR而不是某种类型的INT,那么您有另一个问题。 提供SHOW CREATE TABLE