首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Server忽略行锁提示

Server忽略行锁提示
EN

Stack Overflow用户
提问于 2011-12-04 10:45:03
回答 1查看 1.7K关注 0票数 5

这是一个关于如何锁定值范围的一般性问题(没有其他问题!)当它们还没有在桌子上存在的时候。问题的触发因素是,我想做“插入(如果不存在)”,我不想使用MERGE,因为我需要支持Server 2005。

在第一方面,我:

  1. begin transaction
  2. 使用(SERIALIZABLE, ROWLOCK) + where子句从表中选择数据以重新分配范围
  3. 等等..。

在第二个连接中,我用不匹配第一个连接中的where子句的值向表插入数据。

我希望第二个连接不会受到第一个连接的影响,但它只有在提交(或回滚)第一个连接的事务之后才会结束。

我遗漏了什么?

这是我的测试代码:

首先创建这个表:

代码语言:javascript
复制
CREATE TABLE test
(
    VALUE nvarchar(100)
)

其次,打开新的查询窗口并执行以下操作:

代码语言:javascript
复制
BEGIN TRANSACTION;
SELECT *
FROM  test WITH (SERIALIZABLE,ROWLOCK)
WHERE value = N'a';

第三,打开另一个新的查询窗口并执行以下操作:

代码语言:javascript
复制
INSERT INTO test VALUES (N'b');

注意,第二个查询直到第一个窗口中的事务结束为止

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2011-12-04 10:47:40

您在VALUE上缺少一个索引。

没有这一点,Server就没有任何东西可以打开键范围锁,并将锁定整个表以锁定范围。

然而,即使添加了索引,您仍然会遇到问题中的方案阻塞。RangeS-S锁不会锁定查询中给定的特定范围。相反,它会锁定所选范围的任一键之间的范围。

当没有这样的键,两边的距离锁延伸到无穷大。您需要在ab (例如aa)之间添加一个值,以防止在测试中发生这种情况,并阻止b的插入。

有关此问题的更多信息,请参阅本文中的附加附录:射程锁

票数 8
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/8374760

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档