加速 SQL 查询 DateTime 上的聚合并按

Speedup SQL Query with aggregates on DateTime and group by

我的 MS SQL 数据库中有一个很大(> 1 亿行)table,其中包含以下列:

Id int not null,
ObjectId int not null,
Timestamp datetime not null
State int not null

Id 它是 table 的主键(并且上面有一个聚集索引)。我在 Timestamp 和 ObjectId 上添加了一个非聚集索引(按此顺序)。 ObjectId 中只有大约 2000 个不同的值。我现在要执行以下查询:

SELECT ObjectId, MAX(Timestamp) FROM Table GROUP BY ObjectId

大约需要四秒钟,这对我的应用程序来说太慢了。执行计划表明 97% 的运行时间用于非聚集索引的索引扫描。

在 table 的副本上,我在 ObjectId 和 Timestamp 上创建了聚集索引。结果运行时是相同的,执行计划说它现在正在对聚集索引进行索引扫描。

有没有其他方法可以在不将 table 的数据拆分为多个 table 的情况下改进运行时间?

4 秒对于在具有更多 100M 行的数据库中工作来说还不错。 您可以每天在另一个 table 中存档一些数据以保留历史记录。您可以将所有数据归档到另一个 table 并删除旧的对象更改:

delete from TABLE where Id in (select t1.Id from Table t1, Table t2  
where t1.ObjectId = t2.ObjectId and t1.Timestamp < t2.Timestamp )

对于这个特定的查询,(ObjectId, Timestamp) 上的索引将是最佳的。而且 (ObjectId, Timestamp DESC) 有可能执行得更快。

我可以为您提供另一个答案,添加一个布尔列 LAST,并将 ObjectID 的最后一个 true 更新为 false,然后再插入此 ObjectID 的行,LAST 为 true。在 ObjectID 和 LAST 上创建索引。查询很简单:

SELECT ObjectId, Timestamp FROM Table where LAST = true

不再有 group by 和 fullscan,而是为插入各更新一次。