私は1レコードバックを選択するストアドプロシージャを持っています。ストアドプロシージャは、異なるPC上の複数の異なるアプリケーションから呼び出すことができます。考えられるのは、ストアドプロシージャが処理する必要のある次のレコードを戻し、2つのアプリケーションが同時にストアドプロシージャを呼び出す場合、同じレコードを戻すべきではないということです。私の質問は以下の通りですが、私はできるだけ効率的に質問を書こうとしています(sql 2008)。これよりも効率的に行うことができますか?効率的なトランザクション、レコードロック
CREATE PROCEDURE GetNextUnprocessedRecord
AS
BEGIN
SET NOCOUNT ON;
--ID of record we want to select back
DECLARE @iID BIGINT
-- Find the next processable record, and mark it as dispatched
-- Must be done in a transaction to ensure no other query can get
-- this record between the read and update
BEGIN TRAN
SELECT TOP 1
@iID = [ID]
FROM
--Don't read locked records, only lock the specific record
[MyRecords] WITH (READPAST, ROWLOCK)
WHERE
[Dispatched] is null
ORDER BY
[Received]
--Mark record as picked up for processing
UPDATE
[MyRecords]
SET
[Dispatched] = GETDATE()
WHERE
[ID] = @iID
COMMIT TRAN
--Select back the specific record
SELECT
[ID],
[Data]
FROM
[MyRecords] WITH (NOLOCK, READPAST)
WHERE
[ID] = @iID
END
でそれをすべて行い、この構造を使用することができ、トランザクションすぎるインデックスをフィルタリング安全... –
SELECTの後でUPDATEの前にWAITFOR DELAYを0:2:0にして、SPを実行し、別の接続から同じSPを実行してみてください... –
実際には、私は間違っています! HOLDLOCKはMyRecordsテーブルのREPEATABLEREADと同じ効果を持ちます。 –