admin

SQL查询执行缓慢(对于某些参数值)

sql

我有一个带有多个表的SQL Server 2005数据库。其中一个表用于存储多个设备的时间戳和消息计数器,并具有以下列:

CREATE TABLE [dbo].[Timestamps] (
[Id] [uniqueidentifier] NOT NULL,
[MessageCounter] [bigint] NULL,
[TimeReceived] [bigint] NULL,
[DeviceTime] [bigint] NULL,
[DeviceId] [int] NULL
)

Id是唯一的主键(Guid.Comb),并且在DeviceIdMessageCounter列上都有索引。

我想做的是找到MessageCounter特定设备的最后插入的行(具有最大的行)。

奇怪的是,对 设备号 的查询 4 (以及除No.1以外的所有其他设备)几乎立即返回:

select top 1 * 
   from "Timestamps"
   where DeviceId = 4
   order by MessageCounter desc

但对 设备号的 查询相同 1 永远需要完成:

select top 1 * 
   from "Timestamps"
   where DeviceId = 1 /* this is the only line changed */
   order by MessageCounter desc

最奇怪的是,设备1的 比设备4的 行少 得多:

select count(*) from "Timestamps" where DeviceId = 4
(returns 1,839,210)

select count(*) from "Timestamps" where DeviceId = 1
(returns 323,276).

有人知道我可能做错了什么吗?

[编辑]

从这两个查询的执行计划中,可以清楚地看到,设备1(下图)在索引扫描中创建了大量行:

设备4(上部)和设备1(下部)的执行计划http://img295.imageshack.us/img295/5784/execplans.png

区别在于,当我将索引扫描节点悬停在执行计划图上时:

Device 4 Actual Number of Rows: 1

Device 1 Actual Number of Rows: approx. 6,500,000

6,500,000行是一个非常奇怪的数字,因为我的select count(*)查询为设备1返回了大约300,000行!


阅读 189

收藏
2021-06-07

共1个答案

admin

尝试在上创建索引(DeviceId, MessageCounter DESC)

另外,请尝试以下查询:

select * 
   from "Timestamps"
   where DeviceId = 1
   and MessageCounter = (SELECT MAX(MessageCounter) FROM "Timestamps" WHERE DeviceID = 1)

只是猜测:性能差异可能是因为DeviceId = 1分布在比的更多页面上DeviceId = 4。通过排序,我怀疑您正在疏通所有匹配的页面,即使最终只选择了第一行也是如此。

2021-06-07