在阅读此示例之前,我可以自己理解 rowversion,它反映了记录上最后更新的时间戳。我想它的用法是这样的:首先读取一条记录后,应该达到rowversion列的值。然后在更新该记录之前,应根据从数据库中获取的当前 rowversion 值(在更新前的时间)检查本地存储的 rowversion 值,如果它们不相等,则意味着另一个用户和当前应用程序进行了一些更新应该用自己的策略来处理这种并发情况。
但是,我认为以下示例使问题过于复杂,或者甚至可能是错误的或解释不善(因此会导致混淆):
CREATE TABLE MyTest (myKey int PRIMARY KEY
,myValue int, RV rowversion);
GO
INSERT INTO MyTest (myKey, myValue) VALUES (1, 0);
GO
INSERT INTO MyTest (myKey, myValue) VALUES (2, 0);
GO
DECLARE @t TABLE (myKey int);
UPDATE MyTest
SET myValue = 2 OUTPUT inserted.myKey INTO @t(myKey)
WHERE myKey = 1 AND RV = myValue;
IF (SELECT COUNT(*) FROM @t) = 0
BEGIN
RAISERROR ('error changing row with myKey = %d'
,16 -- Severity.
,1 -- State
,1) -- myKey that was changed
END;
我注意到myValue
这里,它被设置为2
并在 WHERE 子句中用于检查RV
列。据我了解,rowversion 列显然是RV
,但随后它解释了这一点:
myValue 是表示您最后一次读取该行的行的 rowversion 列值。此值必须替换为实际的 rowversion 值
我认为myValue
这里与rowversion没有任何关系,它应该被视为用户数据。所以有了这样的解释,MyTest
表有 2 个 rowversion 列?whilemyValue
显然被声明为int
?
我能想到的一种可能性是myValue
在 WHERE 条件下的理解不同(这意味着它不是myValue
SET 子句中的),它可能只是一个占位符,例如RV
之前读取记录时的读取值。只有这种可能性对我来说才有意义。
所以据我了解,这个例子应该是这样的:
SET myValue = 2 OUTPUT inserted.myKey INTO @t(myKey)
WHERE myKey = 1 AND RV = rowVersionValueFromTheLastTimeReading
我以前听说过,timestamp
但rowversion
对我来说相当新,一旦我尝试找到更多关于它的信息,我发现这个例子让我很困惑。你对此有什么想法?还是我根本不明白 rowversion 的一些神秘用法?谢谢。