关闭

序列化隔离级别Key-Range锁定的真实键范围

发表于:2013-2-05 09:43

字体: | 上一篇 | 下一篇 | 我要投稿

 作者:lzf328    来源:51Testing软件测试网采编

  大家都知道在序列化隔离级别中引入了键范围锁定。键范围锁可防止其他事务插入其键值位于可序列化事务读取的键值范围内的新行,从而确保满足此要求。但是对于锁定的范围真的清楚吗?

  前几天看到有人对于锁范围的疑问,发现锁定的数据比想象的要多。

  下面我们看个例子:

---create tableand insert test data
CREATE TABLE TEST(C1INTprimary key,C2VARCHAR(20))
INSERT INTO testVALUES(1,'TEST'),(2,'TEST'),(3,'EST')
--第一个窗口查询执行

SET TRANSACTIONISOLATIONLEVELSERIALIZABLE
BEGIN TRAN
SELECT * FROM test WHERE C1 BETWEEN 1 AND 3
--第二个窗口查询执行
INSERT INTO testVALUES(100,'TEST')

  按照一般的理解,Rang锁应该会锁定1-3的数据,不允许对其中的数据进行任何修改,所以插入100应该是可以正常执行的。 但是插入100的进程一直被Block无法执行。

  通过sys.dm_tran_locks的resource_description字段我们可以看到“ffffffffffff”,也就是说它的键范围锁是1,2,3到无穷大,而并不少单纯的1,2,3。这个跟我们平常所理解的Rang范围有冲突了。

  查看MSDN有一个 注意:包含的RangeS-S锁数量为n+1,此处n是满足查询条件的行数,也就是说键范围锁的实际范围为键范围+到下一个NEXT值之间的值(包含NEXT值);

  对比上面的例子,可以明白因为表中只有三条数据,相当于所有数据,Next的值就是无穷大,所以Key-range的范围变成了无穷大。如果我们现在插入记录4再执行上面的语句可以看到执行成功(此时锁定的记录为1-4,100并不在这个范围区间,所以可以成功插入)。

  通过上面的例子可以看到Rang Lock的范围比我们一般认识的要大,使用时要格外注意。

《2023软件测试行业现状调查报告》独家发布~

关注51Testing

联系我们

快捷面板 站点地图 联系我们 广告服务 关于我们 站长统计 发展历程

法律顾问:上海兰迪律师事务所 项棋律师
版权所有 上海博为峰软件技术股份有限公司 Copyright©51testing.com 2003-2024
投诉及意见反馈:webmaster@51testing.com; 业务联系:service@51testing.com 021-64471599-8017

沪ICP备05003035号

沪公网安备 31010102002173号