私はBOLフレーズに混乱しています:
「挿入、更新、または削除操作によって変更されたテーブルには、READUNCOMMITTEDおよびNOLOCKを指定できません。SQLServerクエリオプティマイザは、UPDATEまたはDELETEステートメントのターゲットテーブルに適用されるFROM句のREADUNCOMMITTEDおよびNOLOCKヒントを無視します。」[1]
たとえば、私が書く場合
--script 1)
UPDATE Test SET Txt=(Select Txt from TEST WITH(NOLOCK) where ID=1)
WHERE ID=1
エラー(または警告)なしで実行され、おそらく同等です
--script 2)
set transaction isolation level SERIALIZABLE;
begin tran
Declare @nvarm nvarchar(max);
Select @nvarm=Txt from Test where ID=1;
--Select @nvarm;
UPDATE Test SET Txt=@nvarm WHERE ID=1;
commit;
これもエラーや警告なしで実行されます。
それは同等ですか?
テーブルは同じですが、FROMでは、論理的にはソーステーブルであり、別の(物理)テーブルとは異なるソーステーブルで書き直した可能性のあるターゲットテーブルではありません。
--script 3)
select *
into testDup
from TEST;
GO;
UPDATE Test SET Txt=(SELECT Txt FROM TestDUP WITH(NOLOCK) where ID=1)
WHERE ID=1
別のテーブルでNOLOCKを無視する必要があるのはなぜですか?
または、間違っている場合は
、1)と2)でも物理テーブルは同じですが論理的には、「UPDATEまたはDELETEステートメントのターゲットテーブルに適用されるFROM句のNOLOCKヒント」を含むUPDATEの記述方法を質問します。ソース(SELECT内)テーブルとターゲット(UPDATE内)テーブルは異なります。
WITH(NOLOCK)が無視されることを示すUPDATEステートメントを作成するにはどうすればよいですか?
なぜそれをまったく無視する必要があるのですか?無視されますか?
または、それが間違った質問である場合、
なぜ構文は無視されることが保証されているヒントを許可するのですか?
繰り返しになりますが、ドキュメンテーションに書かれているようなステートメントを書くことは不可能(またはそうですか?)であるか、「無視する」という意味がわかりません(無視するという意味は何ですか?またはまったく持つという意味ですか?) ..。。
UPDATE2:
回答は、BOLドキュメント[1]によってアサートされたUPDATEステートメントのFROM句でNOLOCKが無視されない(更新されない)ことを示しています。
さて、この質問の本質:
UPDATEステートメントのFROM句でNOLOCKを無視することが理にかなっている例(コンテキスト)を教えてください。
[1]
テーブルのヒント(Transact-SQL)
SQL Server 2008 R2
http://msdn.microsoft.com/en-us/library/ms187373.aspx