0

我有一个简单的 SQL 命令,它应该从表中读取所有记录,然后将它们全部删除。因为有可能其他人可能会在准确的时刻写入该表,所以我想锁定该表,以确保我删除的所有内容也是我阅读的所有内容。

BEGIN TRAN T1; 
SELECT LotID FROM fsScannerIOInvalidCachedLots WITH (TABLOCK, HOLDLOCK); 
DELETE FROM fsInvalidCachedLots; 
COMMIT TRAN T1;

真正奇怪的是,这用得着。它通过测试工作了一段时间,但现在我猜有些事情发生了变化,因为它正在读取所有内容,但它没有删除任何记录。因此,SQL Server 正在提高 CPU 使用率,因为当它下次运行时,它的执行时间要长得多,我认为这与锁有关。

知道这里会发生什么吗?我都试过TABLOCKTABLOCKX

更新:哦,是的,我忘记提到了,直到下一次阅读程序之后,我才能查询该表。我的意思是,在代码中执行该语句(并且命令和连接被处理)之后,如果我尝试从 Management Studio 中查询该表,它就会挂起,我认为这意味着它仍然被锁定。但是,如果我单步执行调用程序,直到遇到下一个数据库连接,第一次读取表后的那一刻就不再锁定。

4

1 回答 1

1

SELECT从名为 的表中检索数据fsScannerIOInvalidCachedLots,但删除来自名为 的不同表fsInvalidCachedLots

如果在 中运行此查询set xact_abort off,则事务不会因无效表名的错误而中止。事实上,select @@trancount它会告诉你有一个活动的事务,并且select xact_state()会返回 1 表示它是活动的并且没有发生错误

另一方面,随着set xact_abort on,事务被中止。 select @@trancount将返回 0,并且select xact_state()将返回 0(无活动事务)。

有关它们的更多信息,请参阅MSDN 上的@@trancountxact_state()

于 2013-01-22T19:47:09.113 回答