Sql server 无法在快照隔离模式下使用READPAST

Sql server 无法在快照隔离模式下使用READPAST,sql-server,concurrency,transactions,snapshot,isolation-level,Sql Server,Concurrency,Transactions,Snapshot,Isolation Level,我有一个从多个线程调用的进程,它执行以下操作: 启动事务 通过查找IsProcessed=0的下一行,并提示UPDLOCK、HOLDLOCK、READPAST,从工作表中选择工作单位 处理工作单元C和SQL存储过程 提交事务 这样做的想法是,一个线程浸入池中进行下一个工作,并对其进行处理,锁在那里以确保单个工作不会被处理两次。顺序不重要 这一切已经好几个月了。直到今天,我才意识到,尽管启用了快照隔离并将其作为数据库级别的默认设置,但实际的事务创建代码还是手动将隔离级别设置为ReadCommitt

我有一个从多个线程调用的进程,它执行以下操作:

启动事务 通过查找IsProcessed=0的下一行,并提示UPDLOCK、HOLDLOCK、READPAST,从工作表中选择工作单位 处理工作单元C和SQL存储过程 提交事务 这样做的想法是,一个线程浸入池中进行下一个工作,并对其进行处理,锁在那里以确保单个工作不会被处理两次。顺序不重要

这一切已经好几个月了。直到今天,我才意识到,尽管启用了快照隔离并将其作为数据库级别的默认设置,但实际的事务创建代码还是手动将隔离级别设置为ReadCommitted

我适时地将其更改为快照,当然,我立即收到以下消息:

只能在已提交读取或可重复读取中指定READPAST锁

锁定行的主要原因是以这样的方式标记行,即在提交应用标记的事务时,标记将被删除,而锁定似乎是执行此操作的最佳方式,因为除了这些线程之外,此表不会以其他方式读取。如果我使用IsProcessed标志作为锁,那么我可能需要首先进行更新,然后选择我刚刚更新的行,但是我需要使用NOLOCK标志来知道是否有其他线程在一行上设置了该标志

听起来有点乱。最简单的选择是完全放弃快照隔离模式,但步骤3的设计需要它


关于解决此问题的最佳方法,您有什么好主意吗?

将特定事务的隔离级别更改为默认的read committed之外的其他级别,在您的情况下,默认为快照模式。然后,您可以将数据库中的其他工作留在快照中,但代码中的这个特定工作流将不是快照