【发布时间】:2016-10-14 13:46:47
【问题描述】:
我正在设置一个测试用例来证明某个死锁场景,并且需要对正在发生的事情有所了解。 我有一个堆表,通常称为 HeapTable。该表由 2 个事务模拟更新。
交易 1:
BEGIN TRAN
UPDATE HeapTable
SET FirstName = 'Dylan'
WHERE FirstName = 'Ovidiu';
WAITFOR DELAY '00:00:15';
UPDATE HeapTable
SET FirstName = 'Bob'
WHERE FirstName = 'Thierry';
ROLLBACK TRANSACTION
交易 2:
BEGIN TRAN
UPDATE HeapTable
SET FirstName = 'Pierre'
WHERE FirstName = 'Michael';
ROLLBACK TRAN
我首先触发事务 1,紧随其后的是事务 2。正如预期的那样,事务 1 将要求一些独占锁,以及一些意图独占锁。事务 2 将进入并请求同一 RID 上的更新锁:
spid dbid ObjId IndId Type Resource Mode Status
55 5 711673583 0 RID 1:24336:10 X GRANT
57 5 711673583 0 RID 1:24336:10 U WAIT
看到第二个事务要求对同一个 RID 进行更新锁定,我有点惊讶,因为我认为这指向单个记录并且两个更新语句处理不同的数据。我以某种方式期待页面级别的冲突。
当事务 1 的第二次更新启动时,事务 2 将被视为死锁牺牲品,导致事务 2 回滚并完成事务 1。
有人可以解释一下为什么第二个事务需要在同一个 RID 上更新锁,尽管更新了不同的记录?
【问题讨论】:
-
这个 DBA 问题应该在 DBA.SE 上吗?
-
@ajeh 总是发现两者之间的界限有些模糊。如果您认为它在那里有更多用途,我会在那里发布。
-
这里完全没问题。不用担心。
-
在 DBA.SE 上,您会得到专业 DBA 的更多关注,这里有更多的开发人员闲逛。归根结底,这取决于您的个人喜好,但我相信在那里您可以得到那些每天关注这些问题的人的更多关注。
标签: sql-server deadlock