我有一个SP需要10秒才能运行大约10次(每次运行大约一秒钟)。该平台是asp .net,服务器是SQL Server 2005.我已经将表索引(不在PK上),这不是问题。一些警告:
关于可能发生的事情的任何想法?
set ANSI_NULLS ON
go
ALTER PROCEDURE [dbo].[usp_NewSearch]
@Keyword VARCHAR(50),
@SessionID UNIQUEIDENTIFIER,
@time SMALLDATETIME = NULL,
@CityID INT = NULL
AS
BEGIN
SET NOCOUNT ON;
IF @time IS NULL SET @time = GETDATE();
DECLARE @KeywordID INT;
EXEC @KeywordID = usp_SaveKeyword @Keyword;
PRINT 'KeywordID : '
PRINT @KeywordID
DECLARE @SearchID BIGINT;
SELECT TOP 1 @SearchID = SearchID
FROM tblSearches
WHERE SessionID = @SessionID
AND KeywordID = @KeywordID;
IF @SearchID IS NULL BEGIN
INSERT INTO tblSearches
(KeywordID, [time], SessionID, CityID)
VALUES
(@KeywordID, @time, @SessionID, @CityID)
SELECT Scope_Identity();
END
ELSE BEGIN
SELECT @SearchID
END
END
答案 0 :(得分:2)
在SQL Management Studio中启用“显示估计的执行计划” - 执行计划在哪里显示您花时间?它将指导您用于优化查询的启发式(或在本例中不是)。通常,“更胖”的行是要关注的 - 它们是产生大量I / O的行。
不幸的是,即使您告诉我们表模式,只有您能够实际看到SQL如何选择优化查询。最后一件事 - 你有没有关于tblSearches的聚集索引?
答案 1 :(得分:2)
为什么在此查询中使用top 1 @SearchID
而不是max (SearchID)
或where exists
? top
要求您运行查询并从结果集中检索第一行。如果结果集很大,那么在你拿出最终结果集之前,这可能会占用大量资源。
SELECT TOP 1 @SearchID = SearchID
FROM tblSearches
WHERE SessionID = @SessionID
AND KeywordID = @KeywordID;
我没有看到任何明显的原因 - 前面提到的构造中的任何一个应该通过非常便宜的索引查找在语义上等同于此。除非我错过了什么,否则你应该能够做一些像
这样的事情select @SearchID = isnull (max (SearchID), -1)
from tblSearches
where SessionID = @SessionID
and KeywordID = @KeywordID
这应该是相当有效的(除非我遗漏了某些东西)在语义上等同。
答案 2 :(得分:1)
触发器!
他们确实是阴险的。
答案 3 :(得分:1)