MySQL數據庫事務淺談

什麼是事務

數據庫事務( transaction) 是訪問並可能操做各類數據項的一個數據庫操做序列,這些操做要麼所有執行成功,要麼所有執行失敗,是一個不可分割的工做單位。
sql

通俗地說就是指一組sql語句組成的數據庫邏輯處理單元,在這組的sql操做中,要麼所有執行成功,要麼所有執行失敗。數據庫

舉個簡單又經典的例子就是轉帳了,事務A中要進行轉帳,那麼轉出的帳號要扣錢,轉入的帳號要加錢,這兩個操做都必須同時執行成功,爲了確保數據的一致性。併發

事務的特性

在Mysql中事務的四大特性主要包含:原子性(Atomicity)一致性(Consistent)隔離性(Isalotion)持久性(Durable),簡稱爲ACID
性能

  • 原子性: 是指事務的原子性操做,對數據的修改要麼所有執行成功,要麼所有失敗,實現事務的原子性,是基於日誌的Redo/Undo機制
  • 一致性:是指執行事務先後的狀態要一致,能夠理解爲數據一致性。隔離性側重指事務之間相互隔離,不受影響,這個與事務設置的隔離級別有密切的關係。
  • 隔離性:一般來講,一個事務的操做對於其餘的事務的不可見的,也就是說通常而言事務都是獨立的。可是這跟數據庫的隔離級別有關,除了讀未提交這種隔離級別以外,其餘的都是不可見的。
  • 持久性:是指在一個事務提交後,這個事務的狀態會被持久化到數據庫中,也就是事務提交,對數據的新增、更新將會持久化到書庫中。

Undo/Redo日誌

  • Undo日誌記錄某數據被修改前的值,能夠用來在事務失敗時進行rollback;
  • Redo日誌記錄某數據塊被修改後的值,能夠用來恢復未寫入data file的已成功事務更新的數據。

Undo Log 是爲了實現事務的原子性,在MySQL數據庫InnoDB存儲引擎中,還用Undo Log來實現多版本併發控制(簡稱:MVCC)。
日誌

經過Undo/Redo操做,可實現界面操做過程的撤銷和恢復。code

假如某個時刻數據庫崩潰,在崩潰以前有事務A和事務B在執行,事務A已經提交,而事務B還未提交。當數據庫重啓進行 crash-recovery 時,就會經過Redo log將已經提交事務的更改寫到數據文件,而尚未提交的就經過Undo log進行roll back。

事務隔離級別

  • 讀未提交(READ UNCOMMITTED):一個事務還沒提交時,它作的變動就能被別的事務看到。
  •  讀提交(READ COMMITTED):一個事務提交以後,它作的變動纔會被其餘事務看到。 
  • 可重複讀(REPEATABLE READ):一個事務執行過程當中看到的數據,老是跟這個事務在啓動時看到的數據是一致的。固然在可重複讀隔離級別下,未提交變動對其餘事務也是不可見的。
  •  串行化(SERIALIZABLE):對於同一行記錄,「寫」會加「寫鎖」,「讀」會加「讀鎖」,當出現讀寫鎖衝突的時候,後訪問的事務必須等前一個事務執行完成,才能繼續執行。 

隔離級別解決了哪些問題
cdn

髒讀(dirty read):若是一個事務讀到了另外一個未提交事務修改過的數據。
blog


不可重複讀(non-repeatable read):若是一個事務只能讀到另外一個已經提交的事務修改過的數據,而且其餘事務每對該數據進行一次修改並提交後,該事務都能查詢獲得最新值。
事務


幻讀(phantom read):若是一個事務先根據某些條件查詢出一些記錄,以後另外一個事務又向表中插入了符合這些條件的記錄,原先的事務再次按照該條件查詢時,能把另外一個事務插入的記錄也讀出來。
ci


MySQL鎖機制

MySQL中的鎖大體能夠分爲:

  • 共享鎖/讀鎖(Shared Locks):
  • 排他鎖/寫鎖(Exclusive Locks):
  • 間隙鎖:
  • 行鎖(Record Locks):
  • 表鎖:

MyISAM和MEMORY存儲引擎採用的是表級鎖(table-level locking);

BDB存儲引擎採用的是頁面鎖(page-level locking),但也支持表級鎖;

InnoDB存儲引擎既支持行級鎖(row-level locking),也支持表級鎖,但默認狀況下是採用行級鎖。

在四個隔離級別中加鎖確定是要消耗性能的,而讀未提交是沒有加任何鎖的,因此對於它來講也就是沒有隔離的效果,因此它的性能也是最好的。 

相關文章
相關標籤/搜索