SQL Server 2012を使用しています。
2つのクエリを記述しますが、NOLOCK
とUnCommitted
の違いは何ですか?
SELECT lastname, firstname
FROM HR.Employees with (READUNCOMMITTED)
SELECT lastname, firstname
FROM HR.Employees with (NoLock)
NOLOCK:READUNCOMMITTED
と同等です(source:[〜#〜] msdn [〜#〜])
NOLOCK
またはREADUNCOMMITTED
ダーティリードが許可されることを指定します。他のトランザクションが現在のトランザクションによって読み取られたデータを変更できないようにするための共有ロックは発行されません。また、他のトランザクションによって設定された排他ロックは、現在のトランザクションがロックされたデータを読み取ることをブロックしません。ダーティリードを許可すると、同時実行性が高くなる可能性がありますが、データの変更を読み取ってから、他のトランザクションによってロールバックされます
READUNCOMMITTED
およびNOLOCK
ヒントは、データロックにのみ適用されます。それらを含むすべてのクエリwith READUNCOMMITTED and NOLOCK hints
、コンパイルおよび実行中にSch-S(スキーマ安定性)ロックを取得します。このため、同時トランザクションがテーブルのSch-M(スキーマ変更)ロックを保持すると、クエリがブロックされます
フードの下では、同じアクションを実行しています
read-uncommitted
分離レベルは、SQL Server内で最も制限の少ない分離レベルです。これは、開発者がブロッキングの削減を検討する際に人気がある理由でもあります。
背後のnolock
テーブルヒントは、読み取り非コミット分離レベルで実行するのとまったく同じアクションを実行します。
The違いのみ 2つの間の違いは、read-uncommitted
分離レベルは、接続全体のロックメカニズムを決定し、nolock
テーブルヒントは、ヒントを与えるテーブルのロックメカニズムを決定します。
他の人が言ったように、機能の点で違いはありません。
唯一の違いは、一部のテーブルではWITH(NOLOCK)
を選択的に適用できますが、他のテーブルでは適用できないことです。 _READ UNCOMMITTED
_は、セッションのすべてのテーブルにNOLOCK
を適用します。
これを行う場合:
_SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED
SELECT *
FROM Table1 T1
INNER JOIN Table2 T2 ON T1.ID = T2.id
_
機能的には次と同等です:
_SELECT *
FROM Table1 T1 WITH(NOLOCK)
INNER JOIN Table2 T2 WITH(NOLOCK) ON T1.ID = T2.ID
_
ただし、WITH(NOLOCK)
を選択的に適用することもできます。
_SELECT *
FROM Table1 T1 WITH(TABLOCK)
INNER JOIN Table2 WITH(NOLOCK) ON T1.ID = T2.ID
_
文レベルで違いはありません。
セッションレベルでREADUNCOMMITEDを設定できます。ここで、SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTEDを記述する必要があります。
NOLOCKの場合、このヒントをテーブルレベルに配置する必要があるため、更新トランザクションで使用されるすべてのテーブルレベルに配置する必要があります。そのため、クエリでテーブルが参照するすべての場所に配置するのは非常に時間がかかり、時間がかかります。 READ UNCOMMITTEDの場合、すべてのテーブルレベルに配置する必要はなく、セッションレベルまたはクエリレベルに配置するだけで、クエリまたはストアドプロシージャの先頭に書き込むことができます。それを詳しく説明するために小さなデモを見てみましょう。最初にここでデータベースのデフォルトの分離レベルを確認します
CREATE TABLE SAMPLETABLE
(
Col1 INT ,
Col2 VARCHAR(100)
)
INSERT INTO SAMPLETABLE(Col1,Col2)
SELECT 1,'Col1'
Union all
SELECT 2,'Col1'
BEGIN TRANSACTION
Update SAMPLETABLE Set Col2 = 'Value changed' Where col1 =1
Select * from SAMPLETABLE with (nolock)
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED
Select * from SAMPLETABLE
出力は1、両方のクエリでCol1