0

我已經讀取了提交的快照隔離並允許爲我的數據庫隔離ON。我仍然收到一個死鎖錯誤。我很確定我知道發生了什麼......讀取已提交的快照隔離:更新衝突回滾是否顯示爲死鎖?

  1. 第一筆交易在其交易開始時獲得一個序列號。
  2. 第二個在其交易開始時獲得一個較晚的序列號,但在第一個交易已經獲得它(第二個序列號比第一個更新)之後。
  3. 第二個事務首先使其更新語句。當它檢查行版本時,它會看到兩個事務之前的記錄,因爲第一個事務尚未達到更新。它發現該行的序列號處於已提交狀態,並以快樂的方式進行。
  4. 第一個事務處理完畢,就像第二個事務找到相同的已提交序列號,因爲它不會看到第二個事務,因爲它比自己更新。當它嘗試提交時,發現另一個事務已經更新了正在嘗試提交的記錄,並且必須自行回滾。

這是我的問題:這個回滾會在跟蹤中出現死鎖嗎?

+0

。 RE:你的描述表結構和查詢是有用的,因爲描述有些模棱兩可,但無論如何,聽起來像是你可以通過兩個單獨的SSMS窗口中的'BEGIN TRAN'輕鬆地測試自己,然後按照你的理論。 – 2013-03-12 19:55:15

+0

@MartinSmith我可以證明發生了一個僵局;這是一個絕對已知的。問題是我對發生的事情的理解是否正確,或者不同的邏輯是否導致了僵局。查詢不相關,因爲它在並行運行sproc的多個實例時發生在存儲過程的多個位置的多個不同查詢中。我只是想知道更新衝突是否會顯示爲死鎖,或者它會以不同的方式出現。如果它確實表現爲僵局,那麼我有我的解釋;如果它沒有回到繪圖板。 – 2013-03-12 20:02:11

回答

2

在連接到你說的原來的問題中留言:「我只是想知道是否有更新衝突將出現死鎖或者是否會出現一些不同的東西。」當我開始考慮使用快照隔離時,我確實有這些類型的顧慮。最終我意識到READ_COMMITTED_SNAPSHOT和隔離級別SNAPSHOT之間存在顯着差異。

前者使用行版本控制進行讀取,但仍繼續使用獨佔鎖定進行寫入。所以,READ_COMMITTED_SNAPHOT實際上是純悲觀和純樂觀併發控制之間的事情。因爲它使用鎖寫入,更新衝突是不可能的,但是死鎖是可能的。至少在SQL Server中,這些死鎖將被報告爲死鎖,就像正常的悲觀鎖定一樣。

後者(隔離級別SNAPSHOT)是純樂觀的併發控制。行版本控制用於讀取和寫入。死鎖是不可能的,但更新衝突是。後者被報告爲更新衝突而不是死鎖。

0

快照事務回滾,並收到以下錯誤信息:如果你的錯誤是一個死鎖錯誤則是僵局圖將可追溯

Msg 3960, Level 16, State 4, Line 1 
Snapshot isolation transaction aborted due to update conflict. You cannot use snapshot 
isolation to access table 'Test.TestTran' directly or indirectly in database 'TestDatabase' to 
update, delete, or insert the row that has been modified or deleted by another transaction. 
Retry the transaction or change the isolation level for the update/delete statement.