SQL 標準四大隔離級別
SQL 標準定義四種隔離等級,從低到高:
- Read Uncommitted(讀未提交)
- Read Committed(讀已提交)
- Repeatable Read(可重複讀) —— MySQL 預設
- Serializable(可串行化)
低等級支援更高併發,但可能出現髒讀、不可重複讀、幻讀等異常。
各級別詳細特性
1. Read Uncommitted
- 可讀取其他事務未提交的修改(髒讀)。
- 效能不比高等級好多少,極少實際應用。
2. Read Committed
- 僅能讀取已提交事務的修改。
- 同一事務多次 SELECT 可能結果不同(不可重複讀)。
- 大多數資料庫預設等級(MySQL 除外)。
3. Repeatable Read(MySQL 預設)
- 同一事務多次讀取同一資料行,結果一致。
- 理論上會出現幻讀:範圍查詢時,其他事務插入新行導致再次查詢多出「幻影」行。
- InnoDB 透過 MVCC(多版本併發控制)+ 間隙鎖 解決幻讀問題。
4. Serializable
- 最高隔離,強制事務串行執行。
- 每次讀取加共享鎖,解決幻讀但導致大量鎖競爭與超時。
三大異常現象對照
| 異常類型 | 說明 | 發生隔離級別 |
| 髒讀 | 讀到未提交資料,後該事務回滾 | Read Uncommitted |
| 不可重複讀 | 同一事務兩次查詢同一行,結果不同(UPDATE 導致) | Read Committed |
| 幻讀 | 範圍查詢中,其他事務 INSERT/DELETE 導致行數變化 | Repeatable Read(理論上) |
實測驗證過程
設定隔離級別
SET SESSION TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;
SET AUTOCOMMIT = 0;
髒讀演示
客戶端 1(事務 1):更新資料未提交

客戶端 2(事務 2):可讀取到未提交資料

事務 1 回滾後,事務 2 讀到的即為髒資料。
Read Committed 驗證
事務 2 UPDATE 未提交時,事務 1 仍讀到舊值;提交後才讀到新值。同時展示不可重複讀:


Repeatable Read 驗證
事務 2 提交後,事務 1 未提交前,重複讀取結果不變:


Serializable 驗證
事務 1 SELECT 後,事務 2 UPDATE 被共享鎖阻塞;事務 1 提交後,事務 2 獲得排他鎖執行;事務 3 SELECT 又被事務 2 阻塞:


MVCC 與鎖機制補充
- MVCC 僅在 Repeatable Read 與 Read Committed 生效。
- Read Uncommitted 每次讀最新版本;Serializable 全加鎖,無需 MVCC。
- InnoDB 透過 MVCC + 間隙鎖(Next-Key Lock)在 Repeatable Read 下實際上避免了幻讀。
參考資料
《高效能 MySQL》第二版