使用DateTime和group by上的聚合加速SQL查询

时间:2016-09-21 14:51:29

标签: sql sql-server sqlperformance

我的MS SQL数据库中包含以下列的大型(> 1亿行)表:

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

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

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

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

在表的副本上,我在ObjectId和Timestamp上创建了一个聚簇索引。生成的运行时相同,执行计划表示它现在正在执行聚簇索引的索引扫描。

在没有将表格数据拆分成多个表格的情况下,还有其他方法可以改善运行时间吗?

3 个答案:

答案 0 :(得分:1)

我可以给你另一个答案,添加一个布尔列LAST,并在将此ObjectID的当前行插入LAST为true之前将ObjectID的最后一次更新为false。在ObjectID和LAST上创建索引。查询非常简单:

SELECT ObjectId, Timestamp FROM Table where LAST = true

不再需要分组和全扫描,而是每次更新一次以进行插入。

答案 1 :(得分:0)

对于DB中具有更多100M行的工作而言,这种情况还不错4秒。 您可以每天将一些数据存档在另一个表中以保留历史数据。您可以归档另一个表中的所有数据并删除旧的对象更改:

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

答案 2 :(得分:0)

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