SQL:NOLOCK导致查询速度变慢

时间:2011-06-27 17:01:28

标签: sql tsql sql-server-2008

有没有理由为查询添加一个nolock会导致它增加执行时间?

UPDATE TargetTable
      SET col1 = c1.RowCnt,
      col2 = c2.RowCnt
    from TargetTable tt
    join 
    (
      select col3, RowCnt = NULLIF(COUNT(*),0) from Table2 (nolock)
      group by col3
    ) c1 on c1.col3 = tt.ID 
    join
    (
      select col4, RowCnt = NULLIF(COUNT(*),0) from Table2 (nolock) 
      group by col4
    ) c2 on c2.col4 = tt.ID 

      WHERE timestamp BETWEEN @FromDate AND @ToDate
      AND (tt.Client_ID = @Client_ID)

3 个答案:

答案 0 :(得分:2)

NOLOCK提示允许Allocation Order Scans。因此,他们可能会创建一个完全不同的执行计划,一个预计会更快,但事实证明它更慢(例如由于陈旧的统计数据而导致错误的基数估计)。与任何性能问题一样,使用调查方法找出问题的原因。 Waits and Queues是一种非常出色的方法。

答案 1 :(得分:1)

这张表是否有很多写活动?在两种情况下,您确定正确的行会受到影响吗?您是否尝试过使用SET TRANSACTION ISOLATION LEVEL而不是在查询中添加个别提示?

UPDATE tt SET 
    col1 = NULLIF(c1.RowCnt, 0),
    col2 = NULLIF(c2.RowCnt, 0)
FROM dbo.TargetTable AS tt
INNER JOIN 
(
    SELECT col3, RowCnt = COUNT(*)
        FROM dbo.Table2 WITH (NOLOCK)
        GROUP BY col3
) AS c1 ON c1.col3 = tt.ID 
INNER JOIN
(
    SELECT col4, RowCnt = COUNT(*)
        FROM dbo.Table2 WITH (NOLOCK)
        GROUP BY col4
) AS c2 ON c2.col4 = tt.ID 
WHERE tt.[timestamp] BETWEEN @FromDate AND @ToDate
AND tt.Client_ID = @Client_ID;


-- with SQL Server's UPDATE FROM syntax, you should reference the alias in the UPDATE
-- use WITH (NOLOCK), as your current syntax could become an alias in later versions
-- get in the habit of using dbo. prefix and statement terminators
-- are you sure you don't want left joins?

答案 2 :(得分:0)

不是我听过的。我会看一下:
- 更改是表格中的数据,用于更改查询的总体成本 - 锁定正在更新的表的其他服务器活动
- 降低CPU可用性的其他服务器活动
- 使用硬盘的后台操作系统任务