【问题标题】:How can I retrieve rows faster within a time-range, in this simple case?在这种简单的情况下,如何在时间范围内更快地检索行?
【发布时间】:2013-04-02 08:30:14
【问题描述】:

我试图弄清楚为什么在一个时间范围内选择行需要太多时间。

我有一个超过 500 万行的数据库表。

FooTimestamp 列上有一个非唯一、非聚集索引,它是 DateTimeOffset 类型。

当我尝试检索某个时间范围内的某些行时,需要 2 分钟以上。 (当我再次运行它时,由于 MS-SQL Server 2008 的缓存功能,我猜它相对更快)

DECLARE @since datetimeoffset
DECLARE @before datetimeoffset

SET @since ='2013-03-20 00:00:00 +02:00'
SET @before ='2013-03-27 00:00:00 +02:00'

SELECT *
WHERE ([FooTimestamp] >= @since AND [FooTimestamp] <= @before) 

问题: 在从具有数百万条记录的表中检索行时,我应该怎么做才能更快地获得查询结果? (我认为这样一个直截了当的查询需要 2 分钟太多了)

【问题讨论】:

  • 索引是否碎片化?查询计划是什么?
  • 你能把FooTimestamp上的索引聚集起来吗?
  • 否;该列不是 100% 确定具有唯一值
  • 你能告诉你从 FooTimestamp 表中选择了多少行 vs count(*) 吗?我认为你的选择性很低,这就是为什么你在执行计划中有聚集索引扫描操作。在这种情况下,您可以使用覆盖索引(该索引将非常昂贵)加快查询速度 - 通过在包含部分中添加要提取的所有列来更改 FooTimestamp 索引(在您的情况下 - 表中的所有列没有聚集索引列)。
  • 除了索引之外,您可以只检查 BETWEEN 子句以获取相同的查询吗?

标签: sql-server tsql datetime between non-clustered-index


【解决方案1】:

如果你想优化这个特定的查询,我会在你的FooTimeStamp 列上创建一个聚集索引。聚集索引将允许 SQL 服务器使用索引提取所有行数据,而无需进行额外的查找。

这将要求您删除任何现有的聚集索引。如果需要,您可以将其作为非聚集索引添加回来。

与您的评论相反,聚集索引不必是唯一的。另见Do clustered indexes have to be unique?

【讨论】:

    猜你喜欢
    • 2021-01-28
    • 1970-01-01
    • 2012-01-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-11-23
    相关资源
    最近更新 更多