web-dev-qa-db-ja.com

単純な選択クエリはロックを取得しますか?

私はSQL Serverを初めて使用するので、次の非常に単純なselectステートメントがロックを取得するかどうかを知りたいです。

Select * from Student;

ステートメントがbegin tranブロック内で実行されない場合を検討してください。

14
New Developer

はい、デフォルトで読み取る行に共有ロックを適用します(また、クラスター化インデックスのすべてのページで読み取り共有ロックを取得します)。これは、ダーティリードを防ぐために行われます。ただし、これを回避する方法はいくつかあります(SQL Serverにはnolockヒントがあります)。ステートメントがBEGIN TRAN内にない場合、SELECTステートメントの実行後にロックが解放されます。

詳細はここにあります:

http://msdn.Microsoft.com/en-us/library/ms184286(v = sql.105).aspxhttp://www.sqlteam.com/article/introduction -to-locking-in-sql-server

5
WrinkleFree

次の非常に単純なselectステートメントがロックを取得するかどうかを理解したい

SELECTクエリがデフォルトで実行されているのはよくある誤解ですREAD COMMITTEDトランザクション分離レベルでは、ダーティリードを防ぐために常に共有ロックを取得します。

SQL Serverは、共有されていない行レベルのロックの取得を回避できます それらなしでコミットされていないデータを読み取る危険がない場合(より高いレベルのIntent-Shared(IS)ロックが引き続き取得されます)。

共有行ロックareが取られたとしても(おそらく、別の同時トランザクションが行のあるページを変更したため)、SELECTステートメントが完了するずっと前に解放できます。

ほとんどの場合、サーバーが次の行を処理する直前に行が「ロック解除」されます。デフォルトの分離レベルで取得された共有ロックが現在のステートメントの最後まで保持され、transactionの最後まで保持されない場合があります。

現在の分離レベルをNOLOCKテーブルヒントで上書きすることは ほとんどの場合、常に悪い考えです です。

ロックは実装の詳細です。 SQL Serverは、必要に応じてロックを取得し、現在の 分離レベル によって提供されるセマンティック保証を確実に満たすようにします。なぜロックが取得されるのかについて少し知っておくと便利な場合もありますが、ロックを予測しようとすると逆効果になることがよくあります。

SQL Serverは、さまざまな分離レベルを提供します。データ利用者が必要とする保証と動作を提供するものを選択してください。

26
Paul White 9