關係型資料庫都具有一套事務級別,以前的開發和學習過程我很少關注過這個概念,今天蒐集了一些資料,在
結合spring宣告式事務學習的同時,總結一下資料庫的事務級別與操作。
read-uncommitted: 未提交讀 會出現髒讀、不可重複讀、幻讀 ( 隔離級別最低,併發效能高 )
read-committed: 提交讀 會出現不可重複讀、幻讀問題(鎖定正在讀取的行)
repeatable-read: 可重複讀 會出幻讀(鎖定所讀取的所有行)
serializable: 序列化 保證所有的情況不會發生(鎖表)
詳細說明:
未提交讀——這通常稱為 'dirty read':non-locking select 的執行使我們不會看到乙個記錄的可能更早的版本;
因而在這個隔離級別下是非 'consistent' reads;這級隔離級別的運作如同 read committed。處於這個隔離級的
事務可以讀到其他事務還沒有提交的資料。如果這個事務使用其他事務未提交的變化作為計算的基礎,然後那些未
提交的變化被他們的父事務撤銷,則會導致誤差。
提交讀——在乙個事務中已經commit的資料可以在其他事務中看到。如果這個事務頻繁提交的話,其他的大的查詢
事務中可能會得到多個不同的結果。
可重複讀——這是 innodb 預設的事務隔離級。在乙個事務中所有讀都是連續的。
序列化——提供最大程度的隔離,如果每個事務都以這種隔離級執行就會影響mysql的效能,因為需要大量的資源來
使大量事務在任一時刻不被看到。如果乙個事務在執行乙個select操作,另外的事務不允許執行update操作,這個
隔離級別下的select操作被陰式地轉換為 select ... lock in share mode。
不可重複讀的重點是修改 :
同樣的條件 , 你讀取過的資料 , 再次讀取出來發現值不一樣了
幻讀的重點在於新增或者刪除
同樣的條件 , 第 1 次和第 2 次讀出來的記錄數不一樣
mysql innodb儲存引擎的事務隔離級別
檢視innodb系統級別的事務隔離級別:
以下為引用的內容:
mysql> select @@global.tx_isolation;
+-----------------------+
| @@global.tx_isolation |
+-----------------------+
| repeatable-read |
+-----------------------+
1 row in set (0.00 sec)
檢視innodb會話級別的事務隔離級別:
以下為引用的內容:
mysql> select @@tx_isolation;
+-----------------+
| @@tx_isolation |
+-----------------+
| repeatable-read |
+-----------------+
1 row in set (0.00 sec)
修改事務隔離級別:
以下為引用的內容:
mysql> set global transaction isolation level read committed;
query ok, 0 rows affected (0.00 sec)
mysql> set session transaction isolation level read committed;
query ok, 0 rows affected (0.00 sec)
innodb的可重複讀隔離級別和其他資料庫的可重複讀是有區別的,不會造成幻象讀(phantom read),所謂幻象讀,
就是同乙個事務內,多次select,可以讀取到其他session insert並已經commit的資料。下面是乙個小的測試,證明
innodb的可重複讀隔離級別不會造成幻象讀。測試涉及兩個session,分別為session 1和session 2,隔離級別都是
repeateable read,關閉autocommit
以下為引用的內容:
mysql> select @@tx_isolation;
+-----------------+
| @@tx_isolation |
+-----------------+
| repeatable-read |
+-----------------+
1 row in set (0.00 sec)
mysql> set autocommit=off;
query ok, 0 rows affected (0.00 sec)
session 1 建立表並插入測試資料
mysql> create table test(i int) engine=innodb;
query ok, 0 rows affected (0.00 sec)
mysql> insert into test values(1);
query ok, 1 row affected (0.00 sec)
session 2 查詢,沒有資料,正常,session1沒有提交,不允許髒讀
mysql> select * from test;
empty set (0.00 sec)
session 1 提交事務
mysql> commit;
query ok, 0 rows affected (0.00 sec)
session 2 查詢,還是沒有資料,沒有產生幻象讀
mysql> select * from test;
empty set (0.00 sec)
以上試驗版本:
mysql> select version();
+-------------------------+c
| version() |
+-------------------------+
| 5.0.37-community-nt-log |
+-------------------------+
1 row in set (0.00 sec)
spring的宣告式事務的隔離級別與資料庫的如出一轍,共5種級別:
1.isolation_default: 這是乙個platfromtransactionmanager預設的隔離級別,使用資料庫預設的事務隔離級別.
另外四個與jdbc的隔離級別相對應
2.isolation_read_uncommitted: 這是事務最低的隔離級別,它充許令外乙個事務可以看到這個事務未提交的資料。
這種隔離級別會產生髒讀,不可重複讀和幻像讀。
3. isolation_read_committed: 保證乙個事務修改的資料提交後才能被另外乙個事務讀取。另外乙個事務不能讀取該事務未提交的資料
4. isolation_repeatable_read: 這種事務隔離級別可以防止髒讀,不可重複讀。但是可能出現幻像讀。
它除了保證乙個事務不能讀取另乙個事務未提交的資料外,還保證了避免下面的情況產生(不可重複讀)。
5. isolation_serializable 這是花費最高代價但是最可靠的事務隔離級別。事務被處理為順序執行。
除了防止髒讀,不可重複讀外,還避免了幻像讀。
ORACLE資料庫事務隔離級別介紹
兩個併發事務同時訪問資料庫表相同的行時,可能存在以下三個問題 1 幻想讀 事務t1讀取一條指定where條件的語句,返回結果集。此時事務t2插入一行新記錄,恰好滿足t1的where條件。然後t1使用相同的條件再次查詢,結果集中可以看到t2插入的記錄,這條新紀錄就是幻想。2 不可重複讀取 事務t1讀取...
MySQL資料庫事務的隔離級別介紹
在大學學習資料庫的時候就接觸到了事務,但在現在的工作中也沒有使用過,因為平台不支援,在需要保證資料一致性的時候就要自己做,比如有兩條delete語句,當第一條執行成功第二條失敗的時候,就要把第一條刪除的記錄再新增上,非常麻煩。也致使自己對事務沒有真正理解和掌握。使用事務是保證資料的正確性,n條sql...
資料庫的隔離級別介紹
資料庫的隔離級別介紹 隔離 級別的作用是能夠保證多個執行緒同時操作乙個資料時的正確性。1.讀未提交 當你修改或者增加了乙個資料,沒有進行提交導致的髒讀,重複讀,幻讀等。備註 黑色視窗表示視窗一 白色視窗表示視窗二 將事務設定為讀未提交,然後開啟事務。這是事先建立的乙個user表資料 然後對其進行更新...