第18/24周 樂觀併發控制(Optimistic Concurrency)

你們好,歡迎回到性能調優培訓上個星期我經過討論悲觀併發模式拉開了第5個月培訓的序幕。今天咱們繼續,討論下樂觀併發模式(Optimistic Concurrency)html

行版本(Row Versioning)

樂觀併發模式自SQL Server 2005後引入,並基於行版本控制(Row Versioning)原則。行版本控制背後的想法是讀操做(SELECT查詢)再也不須要得到共享鎖(Shared Lock)。不去等待直到成功得到共享鎖(Shared Lock),讀操做是返回行前一個提交的版本。老的,前一個版本被存儲在所謂的版本存儲(Version Store)裏,這個在TempDb裏永駐。寫操做(UPDATE,DELETE語句)明確複製老版本到版本存儲,新版本中含一個指針指向versionstore裏面舊行。下圖詮釋了這個概念。數據庫

 

增長這個指針的一個反作用是每一個記錄會增長額外的14 bytes。這會帶來:併發

  • 堆表上的轉發記錄(Forwarding Records)
  • 彙集表上的頁分裂(Page Splits)

另外,你也要按需計劃和大小TempDb,由於你會引入額外的I/O,在默認配置下會帶來競爭問題。如今讓咱們看看SQL Server提供給你的2個新的樂觀隔離級別(optimistic isolation levels)。性能

樂觀隔離級別(Optimistic Isolation Levels)

自SQL Server 2005起,關係引擎提供2個新的樂觀隔離級別,它們是基於上一部分討論過的行版本控制概念。學習

  • 讀提交快照隔離(Read Committed Snapshot Isolation (RCSI))
  • 快照隔離(Snapshot Isolation (SI))

咱們來詳細看下這2個隔離級別。RCSI提供你基於快照語句級別的隔離。換句話說,SQL Server總會返回你在語句開始前有效的版本。它是提交讀隔離級別(Read Committed Isolation Level)的樂觀實現。所以使用這個隔離級別你會有不可重複讀(Non-Repeatable Reads)。 spa

1 ALTER DATABASE AdventureWorks2012 SET READ_COMMITTED_SNAPSHOT ON
2 GO
3 
4 -- Check if RCSI is now enabled
5 SELECT  name,is_read_committed_snapshot_on
6 FROM sys.databases
7 WHERE database_id = DB_ID('AdventureWorks2012')
8 GO

RCSI的一個好處是對數據庫/應用程序自己它是徹底透明的:你重要在數據庫上啓用它,而後對於每一個查詢新的默認隔離級別是讀提交快照隔離(Read Committed Snapshot Isolation)。所以經過對指定數據庫啓用RCSI,你能夠克服鎖和阻塞問題,即便死鎖問題也很容易。下面代碼顯示了對於給出的數據庫如何啓用RCSI:scala

對於你SELECT查詢,若是你想有重複讀(Repeatable Reads)的樂觀方式,你可使用快照隔離(Snapshot Isolation (SI))隔離級別。快照隔離提供你開箱即用(out of box)的重複讀,這就是說你總拿到在你事務開始前有效的行版本。遺憾的是快照隔離並不徹底透明:版本控制

  • 快照隔離級別必須經過會話明確請求。所以在你的程序裏你須要修改代碼。
  • 你的查詢會執行如所謂的更新衝突(Update Conflicts),SQL Server會回滾事務。所以在你的程序裏你須要相應的進行處理這個狀況。

下面代碼向你展現了對於指定的數據庫,如何啓用快照隔離(Snapshot Isolation),如何請求這個新的隔離級別。指針

 1 -- Enable Snapshot Isolation (SI)
 2 ALTER DATABASE AdventureWorks2012 SET ALLOW_SNAPSHOT_ISOLATION ON
 3 GO
 4 
 5 -- Check if SI is now enabled
 6 SELECT name, snapshot_isolation_state,  snapshot_isolation_state_desc
 7 FROM sys.databases
 8 WHERE database_id = DB_ID('AdventureWorks2012')
 9 GO
10 
11 USE AdventureWorks2012
12 GO
13 
14 -- Setting the Isolation Level to Snapshot Isolation
15 SET TRANSACTION ISOLATION LEVEL SNAPSHOT
16 GO

小結

今天你學習了自SQL Server 2005起支持的2個樂觀隔離級別。提交讀快照隔離(Read Committed Snapshot Isolation (RCSI))提供你基於語句級別的隔離,快照隔離(Snapshot Isolation (SI))提供你基於事務級別的隔離,由於2個隔離級別使在永駐在TempDb裏的版本存儲,對於TempDb你須要仔細計劃和指定標準。code

下週我會談下SQL Server 裏鎖和阻塞發生的問題:鎖升級(Lock Escalations)。請繼續關注!

圍觀PPT:

0928_18_樂觀併發控制.rar

相關文章
相關標籤/搜索