資料庫技術 事務 0001 衝突情況與隔離級別

2021-09-23 19:35:52 字數 3373 閱讀 6964

基礎技術:

丟失更新(lost update)

第一類丟失更新:

a事務撤銷時,把已經提交的b事務的更新資料覆蓋了。這種錯誤可能造成很嚴重的問題:

a事務在撤銷時,"不小心"將b事務已經轉入賬戶的金額給抹去了。

第二類丟失更新:

a事務覆蓋b事務已經提交的資料,造成b事務所做操作丟失:

上面的例子裡由於轉賬事務覆蓋了取款事務對存款餘額所做的更新,導致銀行最後損失了100元,相反如果轉賬事務先提交,那麼使用者賬戶將損失100元。

髒讀(dirty read)

當乙個事務讀取另乙個事務尚未提交的修改時,產生髒讀。

1.公司發工資了,領導把5000元打到singo的賬號上。

2.但是該事務並未提交,而singo正好去檢視賬戶,發現工資已經到賬,是5000元整,非常高興。

3.可是不幸的是,領導發現發給singo的工資金額不對,是2000元,於是迅速回滾了事務,修改金額後,將事務提交。

4.最後singo實際的工資只有2000元,singo空歡喜一場。

出現上述情況,即我們所說的髒讀。

兩個併發的事務,"事務a:領導給singo發工資"、"事務b:singo查詢工資賬戶",事務b讀取了事務a尚未提交的資料。

不可重複讀(non-repeatable read)

同一查詢在同一事務中多次進行,由於其他提交事務所做的修改或刪除,每次返回不同的結果集,此時發生非重複讀。

即,同樣的條件, 你讀取過的資料, 再次讀取出來發現值不一樣了,只需要鎖住滿足條件的記錄即可解決(乙個事務無論讀寫均不允許其他事物操作行資料,悲觀行鎖)。

1.singo拿著工資卡去消費,系統讀取到卡里確實有2000元。

2.而此時她的老婆也正好在網上轉賬,把singo工資卡的2000元轉到另一賬戶,並在singo之前提交了事務。

3.當singo扣款時,系統檢查到singo的工資卡已經沒有錢,扣款失敗,singo十分納悶,明明卡里有錢,為何不能扣款。

出現上述情況,即我們所說的不可重複讀。

兩個併發的事務,"事務a:singo消費"、"事務b:singo的老婆網上轉賬",事務a事先讀取了資料,事務b緊接了更新了資料,並提交了事務,而事務a再次讀取該資料時,資料已經發生了改變。

幻像讀(phantom read)

同一查詢在同一事務中多次進行,由於其他提交事務所做的插入操作,每次返回不同的結果集,此時發生幻像讀。

即,同樣的條件, 第1次和第2次讀出來的記錄數不一樣,要鎖住滿足條件及其相近的記錄(悲觀表鎖)。

1.singo的老婆工作在銀行部門,她時常通過銀行內部系統檢視singo的信用卡消費記錄。

2.有一天,她正在查詢到singo當月信用卡的總消費金額(select sum(amount) from transaction where month = 本月)為80元

3.而singo此時正好在外面胡吃海塞後在收銀台買單,消費1000元,即新增了一條1000元的消費記錄(insert transaction ... ),並提交了事務

4.隨後singo的老婆將singo當月信用卡消費的明細列印到a4紙上,卻發現消費總額為1080元,singo的老婆很詫異,以為出現了幻覺

幻讀就這樣產生了。

資料庫事務的隔離級別有4個,由低到高依次為readuncommitted、readcommitted、repeatableread、serializable,這四個級別可以逐個解決髒讀、不可重複讀、幻讀這幾類問題。(所有級別都能解決更新丟失)

注意:我們討論隔離級別的場景,主要是在多個事務併發的情況下,因此,接下來的講解都圍繞事務併發。

read uncommitted 讀未提交

允許髒讀取但不允許更新丟失。

如果乙個事務已經開始寫資料,則另外乙個資料則不允許同時進行寫操作,但允許其他事務讀此行資料。

該隔離級別可以通過"排他寫鎖"實現。未提交讀事務允許其他事務讀寫該行資料,未提交寫事務禁止其他事務寫該行資料(單允許讀)。

事務隔離的最低級別,僅可保證不讀取物理損壞的資料。

與read committed隔離級相反,它允許讀取已經被其它使用者修改但尚未提交確定的資料。

當隔離級別設定為read uncommitted時,就可能出現髒讀。

read committed讀提交

允許不可重複讀取但不允許髒讀取。

這可以通過"瞬間共享讀鎖"和"排他寫鎖"實現。未提交讀事務允許其他事務讀寫該行資料,未提交寫事務禁止其他事務讀寫該行資料。

在此隔離級下,select命令不會返回尚未提交(committed) 的資料,也不能返回髒資料。

當隔離級別設定為read committed時,避免了髒讀,但是可能會造成不可重複讀。

大多數資料庫的預設級別就是read committed,比如sql server , oracle。

repeatable read重複讀

禁止不可重複讀取和髒讀取,但是有時可能出現幻影資料。

這可以通過"共享讀鎖"和"排他寫鎖"實現。未提交讀事務禁止其他事務寫該行資料(但允許讀),未提交寫事務禁止其他事務讀寫該行資料。

在此隔離級下,用select命令讀取的資料在整個命令執行過程中不會被更改。

此選項會影響系統的效能,非必要情況最好不用此隔離級。

mysql的預設隔離級別就是repeatable read。

serializable序列化

提供嚴格的事務隔離。

它要求事務序列化執行,事務只能乙個接著乙個地執行,但不能併發執行。

如果僅僅通過"行級鎖"是無法實現事務序列化的,必須通過其他機制保證:新插入的資料不會被剛執行查詢操作事務訪問到(表級鎖/或者相關行的鎖)。

事務隔離的最高端別,事務之間完全隔離。如果事務在可序列讀隔離級別上執行,則可以保證任何併發重疊事務均是序列的。

serializable是最高的事務隔離級別,同時代價也花費最高,效能很低,一般很少使用,在該級別下,事務順序執行,不僅可以避免髒讀、不可重複讀,還避免了幻像讀。

資料庫 事務 併發控制技術

事務指的是連續的對資料庫操作的集合,對於乙個事務中的所有的資料庫操作,要麼全部成功,要麼全部失敗。允許多個使用者同時使用的資料可系統為多使用者資料庫系統。多使用者資料庫系統的特點是 在同一時刻,併發執行的事務數量可以達到成千上萬個。多事務執行方式有三種 1 事務的序列執行 每個時刻只有乙個事務執行,...

0001 Oracle資料庫安裝

一 安裝oracle資料庫系統 二 設定監聽程式 在 開始 中找到oracle11gr2目錄,在 配置和移植工具 下找到 net configuration assistant 進入監聽設定,按照預設設定一路下去即可 三 建立資料庫例項 在 配置和移植工具 下找到database configura...

資料庫事務

事件是訪問並可能更新各種資料項的乙個程式執行單元。事件由事務開始與事務結束之間執行的全體操作組成。為了保證資料完整性,資料庫系統需要維護事務的以下性質 原子性 atomicity 事務中的操作要麼全部成功,要麼全部失敗。一致性 consistency 事務執行前後要保持資料庫的一致性。隔離性 iso...