2009-08-14 52 views
0

我以前用XML列發佈了一個關於我的查詢速度的問題。經過一些進一步的調查後,我發現它不像以前所想的那樣與XML相關。表格模式和查詢非常簡單。有超過800K行,一切都運行平穩,但沒有記錄的增加,它需要幾分鐘的時間才能運行。SQL Server速度

表:

/****** Object: Table [dbo].[Audit] Script Date: 08/14/2009 09:49:01 ******/ 
SET ANSI_NULLS ON 
GO 
SET QUOTED_IDENTIFIER ON 
GO 
CREATE TABLE [dbo].[Audit](
    [ID] [int] IDENTITY(1,1) NOT NULL, 
    [PID] [int] NOT NULL, 
    [Page] [int] NOT NULL, 
    [ObjectID] [int] NOT NULL, 
[Data] [nvarchar](max) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL, 
    [Created] [datetime] NULL, 
CONSTRAINT [PK_Audit] PRIMARY KEY CLUSTERED 
(
    [ID] ASC 
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF,   ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY] 
) ON [PRIMARY] 

查詢:

SELECT * 
FROM Audit 
WHERE PID = 158 
AND Page = 2 
AND ObjectID = 93 

查詢只返回26條記錄和有趣的事情是,如果我加入「TOP 26」查詢不到執行其次,如果我將其更改爲「TOP 27」,則需要一分鐘。即使我將查詢更改爲SELECT ID,也無關緊要。

任何幫助表示讚賞

回答

1

爲什麼不加覆蓋索引的頁面和對象ID列和收工?

+0

你忘了PID ... – Guffa 2009-08-14 20:51:47

+0

是的,對不起:)你應該索引任何東西出現在where子句。我沒有列出PID,因爲我誤解爲ID,這是主鍵,並且已經有索引。 – 2009-08-14 22:23:39

+0

那麼,它實際上可以創建一個沒有索引的主鍵... – Guffa 2009-08-14 23:45:52

1

我認爲你必須爲你想要搜索的列添加非唯一索引。編制索引肯定會縮短搜索時間。在SELECT查詢中請求單列還是多列不會有什麼區別。單獨比較行所需的時間需要通過索引來減少。

6

您有一個關於ID的索引,但您的查詢正在使用其他列。因此,您可能正在進行全表掃描。更改爲SELECT ID沒有任何區別,因爲它不在WHERE子句中的任何位置。

當您詢問TOP 26時很快,因爲它沒有任何ORDER BY子句就可以退出,一旦它找到26行。將它改爲TOP 27意味着,一旦它找到前26(根據你的帖子,所有匹配),它不能退出尋找;它必須繼續搜索,直到找到第27個匹配的行或到達數據的末尾。

一個SHOW PLAN會很快顯示你的問題。

+0

關於爲什麼TOP 27需要更長時間的信息。我沒有想到這一點。 – 2009-08-14 20:00:58

2

爲PID,Page和ObjectID字段添加一個索引。

0

26行可能接近表格的起始位置,當您掃描時發現它們快速並中止掃描的其餘部分,當查找不存在的第27個掃描整個表時,這是慢的!

尋找這些類型的問題時嘗試這種從查詢管理工作室:

運行:_set SHOWPLAN_ALL ON_
然後運行查詢,查找單詞「SCAN」,他們是mostlikely查詢運行的位置慢,找出爲什麼沒有使用索引。

在這種情況下,您需要添加一個索引。我通常會根據查詢數據的方式添加一個索引,如果您始終擁有以下三項之一:PID,Page和Object ID,首先在該列中添加一個索引,並在該索引中添加另一列(如果您有時具有該值太。等