在嵌套查询中放置WITH(NOLOCK)

1 sql t-sql sql-server sql-server-2008

在以下查询中我将放置在哪里WITH(NOLOCK)

SELECT *
FROM   (SELECT *
        FROM   (SELECT *
                FROM   (SELECT *
                        FROM   (SELECT *
                                FROM   dbo.VBsplit(@mnemonicList, ',')) a) b
                       JOIN dct
                         ON dct.concept = b.concept
                WHERE  b.geo = dct.geo) c
               JOIN dct_rel z
                 ON c.db_int = z.db_int) d
       JOIN rel_d y
         ON y.rel_id = d.rel_id
WHERE  y.update_status = 0
GROUP  BY y.rel_id,
          d.concept,
          d.geo_rfa 
Run Code Online (Sandbox Code Playgroud)

Aar*_*and 10

您不应该NOLOCK在该查询中放置任何位置.如果你试图阻止读者阻止作者,一个更好的选择是READ COMMITTED SNAPSHOT.当然,你应该阅读这个,就像你应该NOLOCK在盲目地将它放入你的查询之前阅读:

此外,由于您正在使用SQL Server 2008,您应该VBSplit()使用表值参数替换您的函数 - 这将比分割字符串更有效,即使函数在CLR中被隐藏了.

首先,创建一个可以容纳适当字符串的表类型.我将假设列表保证是唯一的,并且没有单独的助记符字可以> 900个字符.

CREATE TYPE dbo.Strings AS TABLE(Word NVARCHAR(900) PRIMARY KEY);
Run Code Online (Sandbox Code Playgroud)

现在,您可以创建一个采用此类型参数的过程,并在一个位置设置您选择的隔离级别:

CREATE PROCEDURE dbo.Whatever
  @Strings dbo.Strings READONLY
AS 
BEGIN
  SET NOCOUNT ON;
  SET TRANSACTION ISOLATION LEVEL --<choose wisely>;

  SELECT -- please list your columns here instead of *
    FROM @Strings AS s
    INNER JOIN dbo.dct -- please always use proper schema prefix
    ON dct.concept = s.Word
    ...
END
GO
Run Code Online (Sandbox Code Playgroud)

现在,您只需从应用程序中传递一个集合(例如DataTable),无论是C#还是其他任何东西,都不必组装或解构一个混乱的逗号分隔列表.