6

WITH (ROWLOCK) を使用してテーブルの 1 行を更新しましたが、"sp_lock" を実行すると、テーブル全体がロックされていることがわかります。そのため、トランザクションがコミットされる前に、他のトランザクションはテーブルの他の行を更新できません。「WITH (ROWLOCK)」が有効にならないのはなぜですか?

以下のクエリを行ロックで使用しています。

DELETE FROM DefDatabaseSession  WITH (ROWLOCK) WHERE ProcessName='test';

同じテーブルの異なる行に対して同じ削除操作を実行している他のトランザクションから同時に、例外が発生しています

[SQLServer JDBC ドライバー][SQLServer]ロック要求のタイムアウト期間を超えました。; ネストされた例外は java.sql.SQLException: [newscale][SQLServer JDBC Driver][SQLServer]Lock request time out period exceeded.: com.newscale.bfw.udkernel.kernel.UdKernelException: udconfig.defdbsession.delete; SQL の uncategorized SQLException [DELETE FROM DefDatabaseSession WHERE ProcessName = ?]; SQL 状態 [HY000]; エラーコード [1222]; [newscale][SQLServer JDBC ドライバー][SQLServer]ロック要求のタイムアウト期間を超えました。; ネストされた例外は java.sql.SQLException: [newscale][SQLServer JDBC Driver][SQLServer]ロック要求のタイムアウト期間を超えました。

4

2 に答える 2

0

私の推測では、 にインデックスがないProcessNameため、クエリは完全なテーブル スキャンを実行する必要があるため、すべての行が読み取られる (そして削除の候補になる可能性がある) ため、すべての行をロックするよりもテーブル全体をロックする方が効率的です。 .

インデックスを定義してみてください:

CREATE INDEX DefDatabaseSession_ProcessName ON DefDatabaseSession(ProcessName);

説明を行うことで、クエリプランを見つけることができます。

EXPLAIN DELETE FROM DefDatabaseSession  WITH (ROWLOCK) WHERE ProcessName='test';
于 2013-08-04T14:09:40.600 に答える