下面提到五种隔离级别摘要...如果我错了请纠正我: -
答案 0 :(得分:1)
您需要首先了解隔离级别解决的下划线问题。
尝试在两个连接上玩游戏。首先运行连接1脚本然后连接2脚本而不提交任何内容。执行完两个脚本后,尝试提交连接1.
READ UNCOMMITTED - 在此隔离级别下运行的连接可以读取已modified by other transactions
但尚未提交的行。
READ COMMITTED - 在此隔离级别下运行的连接无法读取已修改但未由其他事务提交的数据。
REPEATABLE READ - 在此隔离级别下运行的事务无法读取已被修改但尚未由其他事务和提交的数据,其他任何事务都无法修改已有的数据在此事务完成之前,此事务已读取此事务。这是通过在此事务读取的记录上放置共享锁来完成的。拥有共享锁定记录,在此事务完成之前,没有其他事务可以修改此记录。
SERIALIZABLE - 与可重复读取相同的条件,增加了一个条件,即其他事务无法插入新行,其键值将落入由任何语句读取的键范围内当前事务完成之前的当前事务。 将记录视为在日期范围之间插入记录。您正尝试在另一个连接读取的日期范围之间插入记录。
连接1
SET TRANSACTION ISOLATION LEVEL READ COMMITTED
BEGIN TRAN
UPDATE tbl SET Col1 = 'Dummy' WHERE ID = 1
--NO COMMIT YET
连接2
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED
BEGIN TRAN
SELECT * FROM tbl WHERE ID = 1 -- will return you 'Dummy' if script
on connection 1 executed first. Since transaction on
connection 1 hasn't been committed yet, you did a dirty
read on connection 2.
--NO COMMIT YET
连接1
SET TRANSACTION ISOLATION LEVEL REPEATABLE READ
BEGIN TRAN
SELECT * FROM tbl WHERE id = 5 --Issue shared lock. This prevents
other transactions from modifying any
rows that have been read by the current transaction.
--Not committed yet
连接2
SET TRANSACTION ISOLATION LEVEL READ COMMITTED
BEGIN TRAN
SELECT * FROM tbl WHERE id = 5
UPDATE tbl set name='XYZ' WHERE ID = 5 -- this will wait until transaction
at connection 1 is completed.
(Shared lock has been taken)
--Not committed yet
连接1
SET TRANSACTION ISOLATION LEVEL SERIALIZABLE
BEGIN TRAN
SELECT * FROM tbl WHERE Age BETWEEN 5 AND 15 -- This will issue range lock
--Not committed yet
连接2
SET TRANSACTION ISOLATION LEVEL READ COMMITTED
BEGIN TRAN
INSERT INTO tbl (Age) VALUES(4) -- Will insert successfully
INSERT INTO tbl (Age) VALUES(7) -- this will wait until transaction
at connection 1 is completed.
(Range lock has been taken)
--Not committed yet