MySQL學習

Mysql 讀書筆記 - 《高性能MySQL》

mysql 存儲引擎結構: 將查詢處理,及其餘系統任務和數據的存儲/提取相分離。mysql

mysql邏輯架構

mysql服務邏輯架構圖sql

mysql服務邏輯架構圖

鏈接/線程處理

  • 每一個客戶端都會在服務器進程中擁有一個線程,該鏈接的查詢只會在這個單獨的線程中執行。
  • 客戶端鏈接時須要對其進行認證
  • 鏈接成功後會繼續驗證客戶端是否有執行特定查詢的權限

優化與執行

  • mysql會解析查詢,建立內部數據結構--解析樹

併發控制

mysql 控制併發的兩個層面:服務器層與存儲引擎層數據庫

讀寫鎖

實現一個由兩種類型的鎖組成的鎖系統來解決問題
這兩種類型的鎖被稱爲共享鎖排他鎖,也叫讀鎖寫鎖安全

讀鎖是共享的,相互不干擾的。
寫鎖是排他的,即寫鎖會阻塞其餘的寫鎖和讀鎖服務器

讀寫鎖確保在給定時間內,只有一個用戶能執行寫入,而且防止其餘用戶讀取正在寫入的同一資源數據結構

鎖粒度

  • 任何狀況下,在給定的資源上,鎖定的數據越少,系統的併發程度越高(前提是相互之間不發生衝突)
  • 加鎖也須要消耗資源

綜合上述兩點,引出了鎖策略架構

鎖策略,即在鎖的開銷和數據的安全性之間尋求平衡併發

兩種重要的鎖策略:性能

  • 表鎖

表鎖是mysql最基本的鎖策略,也是開銷最小的策略,他會鎖定整張表優化

  • 行級鎖

行級鎖能夠最大程度的支持併發處理,也帶來了最大的鎖開銷。行級鎖只在存儲引擎層實現,在服務器層沒有實現

事物

什麼是事物,事物是一組原子性的SQL查詢,或者說一個獨立的工做單元。事物內的語句,要麼所有執行成功,要麼所有執行失敗

事物的ACID
事物的ACID表示原子性、一致性、隔離性、持久性

一個良好的事物處理系統,必須具有這些標準的特徵

  • 原子性:一個事物必須被視爲一個不可分割的最小工做單元,整個事物中的全部操做要麼所有執行成功,要麼所有執行失敗
  • 一致性:數據庫老是從一個一致性狀態轉換到另一個一致性的狀態
  • 隔離性:一個事物所作的修改在最終提交以前,其餘事物是不可以看到的。
  • 持久性:事物一旦提交,所作的修改就會保存到數據庫中

事物同鎖粒度同樣,一樣會增長系統的開銷。

隔離級別

在SQL標準中定義了四種隔離級別,每一種級別都規定了一個事物中所作的修改,哪些在事物內和事物間是可見的,哪些是不可見的
四種隔離級別:

  • READ UNCOMMITTED (未提交讀) 事物中的修改,即便沒有提交,對其餘事物也是可見的。所以會產生髒讀,即事物讀取未提交的數據。這個級別會產生不少問題,但在性能上卻不比其餘級別好太多。
  • READ COMMITTED (提交讀) 此級別爲大多數數據庫系統的默認隔離級別(MYSQL不是)。此級別下,一個事物從開始直到提交以前,所作的任何修改對其餘事物都是不可見的。此級別下,執行一樣的查詢,可能會獲得不同的結果。所以此級別有時也叫不可重複讀
  • REPEATABLE READ (可重複讀)
    此級別是MYSQL默認的事物隔離級別。
    此級別保證在同一個事物中屢次讀取一樣的記錄的結果是一致的。可是,此級別還有另一個沒法解決的問題,幻讀。幻讀,指的是當某個事物在讀取某個範圍內的記錄時,其餘的事物在該範圍內插入了新的記錄,當事物在此讀取該範圍的記錄時,會產生幻行.InnoDB 和 XtraDB存儲引擎經過多版本併發控制解決了幻讀的問題。
  • SERIALZABLE (可串行化)
    此級別時事物的最高級別。它經過強制事物串行執行,避免幻讀問題,可是會致使大量的超時和鎖爭用的問題。他的原理是在讀取的每一行數據上都加鎖。

死鎖

死鎖是指兩個或者多個事物在同一資源上相互佔用,並請求鎖定對方佔用的資源,從而致使的惡性循環的現象。當多個事物以不一樣的順序鎖定資源時,就可能會產生死鎖。
數據庫系統實現各類死鎖檢測和死鎖超時機制
InnoDB 處理死鎖的方法:將持有最少行級排他鎖的事物進行回滾。

事物日誌

目前大多數存儲引擎都採用預寫式日誌

預寫式日誌:存儲引擎在修改表的時候只須要修改其內存拷貝,再吧該修改行爲記錄到持久在硬盤上的事物日誌中,而不用每次都將修改的數據自己持久到磁盤。事物日誌持久後,內存中被修改的數據在後臺能夠慢慢地刷回到磁盤。

MySQL中的事物

MySQL提供的兩種事務型存儲引擎:InnoDB,NDB Cluster。

MySQL的自動提交機制

  • MySQL中默認採用自動提交模式,若是不是顯示地開始一個事物,每一個查詢都會被看成一個事物執行提交操做。
    能夠經過設置AUTOCOMMIT變量來改變自動提交模式

  • AUTOCOMMIT=0 時,全部的查詢都在一個事物中,直到顯示執行COMMITROLLBACK時,事物結束,同事開啓新的事物。

    還有些命令會強制執行COMMIT提交當前活動的事物 ,例如DDL語句

  • 能夠經過執行SET TRANSACTION ISOLATION LEVEL XXX來設置隔離級別,新的級別將會在下個事物開始生效。

  • 設置當前回話的隔離級別SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED

在事物中混合使用存儲引擎

MySQL中服務層無論理事務,事務都是由下層存儲引擎實現的。

若是在事物中混合使用了事務型和非事務型表,在正常提交狀況下沒有任何問題,可是一旦事物須要回滾時,非事務型表上的操做就沒法撤銷,這樣就會形成數據庫不一致的問題

顯示和隱式鎖定

  • 隱式鎖定 InnoDB 會根據隔離級別在須要的時候自動加鎖,在事物的執行過程當中,隨時均可以執行鎖定,可是隻有在執行COMMITROLLBACK時候進行鎖釋放。
  • 顯示鎖定
    SELECT ... LOCAK IN SHARE MODE
    SELECT ... FOR UPDATE

多版本併發控制

多版本併發控制(MVCC)的實現,是經過保存數據在某個時間點的快照來實現的。根據事物的開始時間不一樣,每一個事物對同一張表,同一個時刻看到的數據可能不同,同一個事物無論須要執行多長時間,看到的數據都是一致的。

InnoDB 的 MVCC

經過在每行記錄後面保存兩個隱藏的列來實現。一個保存的是行的建立時間,一個保存的是行的過時時間。其中存儲的是系統版本號,每開始一個新的事物,系統版本號都會自動遞增,事物開始時的系統版本號做爲事物的版本號。

InnoDB MVCC具體操做:

  • SELECT 時,查詢複合如下條件的數據:
    • 建立時間版本早於或等於當前事物版本。 -- 這樣能夠確保查詢的數據在事物開始前就已經存在,或者由事物自己插入
    • 刪除時間未定義或大於當前事物版本。 -- 這樣能夠確保查詢到的數據在事物開始以前未被刪除
  • INSERT 時, 爲新插入的每一行保存當前事物版本號做爲建立時間
  • DELETE 時, 爲刪除的每一行保存當前事物版本號做爲刪除時間
  • UPDATE 時, 新插入一行記錄,保存當前事物版本號做爲建立時間,同事保存事物版本號做爲原來行的刪除時間

MVCC 只在 REPEATABLE READ 和 READ COMMITTED兩個隔離級別下工做

相關文章
相關標籤/搜索