我正在尝试创建一个包含最新版滚动(SRC)表的存档(TGT)。 SRC可能包含多个版本和重复项,但TGT应仅包含唯一的最新行。
有4列 - A,B,C和D形成一个UNIQUE键,第五列E代表一个版本号。
所以如果我加入以下内容:
SRC.A = TGT.A AND SRC.B = TGT.B AND SRC.C = TGT.C AND SRC.D = TGT.D
应该有两个结果 - 匹配或不匹配。但是,如果有匹配,我有一个我想申请的子条件,所以我真正想要找到3个可能的结果:
匹配AND SRC.E > TGT.E
=> SRC是更高版本,因此TGT行应该更新
匹配AND SRC.E <= TGT.E
=&gt; SRC较旧或相同,因此不应该做任何事情
不匹配=&gt;应将SRC行插入TGT
我遇到的问题是结果2和3,因为MERGE
只允许两个WHEN MATCHED
子句,在这种情况下,一个必须是UPDATE
而另一个必须是一个DELETE
。我真的想要一个UPDATE
和一个&#34;什么都不做&#34;
这些方面的东西:
MERGE
Target AS TGT
USING
Source AS SRC ON SRC.A = TGT.A AND SRC.B = TGT.B AND SRC.C = TGT.C AND SRC.D = TGT.D
WHEN MATCHED AND SRC.E > TGT.E -- SRC is newer, so update TGT
THEN UPDATE SET TGT.E = SRC.E
WHEN MATCHED -- "AND SRC.E <= TGT.E” is implied...
-- SRC is older or equal, so do nothing
WHEN NOT MATCHED BY TARGET -- SRC doesn't exist in TGT, so insert it
THEN INSERT VALUES (SRC.A, SRC.B, SRC.C, SRC.D, SRC.E)
这可能吗?它是否像重新安排我的加入一样简单?
我尝试删除第二个WHEN MATCHED
子句,但之后会导致重复键警告,因为它会尝试插入旧记录
我使用SQL Server 2016,如果它改变了什么
答案 0 :(得分:0)
您可以使用CTE或子查询操作源表,如下例所示。
;WITH MostRecentSourceVersion AS
(
SELECT
S.A,
S.B,
S.C,
S.D,
E = MAX(S.E) -- Assuming the most recent is the MAX
FROM
Source AS S
GROUP BY
S.A, -- Your keys here
S.B,
S.C,
S.D
)
MERGE
Target AS TGT
USING
MostRecentSourceVersion AS SRC
ON
SRC.A=TGT.A AND SRC.B=TGT.B AND SRC.C=TGT.C AND SRC.D=TGT.D
WHEN MATCHED AND SRC.E > TGT.E -- SRC is newer, so update TGT
THEN UPDATE SET TGT.E = SRC.E
WHEN NOT MATCHED BY TARGET -- SRC doesn't exist in TGT, so insert it
THEN INSERT VALUES (SRC.A, SRC.B, SRC.C, SRC.D, SRC.E);
通过这种方式,您可以确定,如果匹配,则始终为1。
如果您需要多于1列来确定最新版本(必须在行号= 1的位置进行过滤),您也可以使用ROW_NUMBER()
。
答案 1 :(得分:0)
不确定是否适合回答我自己的问题,但我找到了似乎的解决方案(如果您发现问题,请纠正我!)并认为我将分享给未来的访客:
MERGE
Target AS TGT
USING
(
SELECT TOP 1 WITH TIES
A, B, C, D
FROM
Source
ORDER BY
ROW_NUMBER() OVER (PARTITION BY A, B, C, D ORDER BY E DESC)
) AS SRC
ON
SRC.A = TGT.A
AND SRC.B = TGT.B
AND SRC.C = TGT.C
AND SRC.D = TGT.D
WHEN MATCHED AND SRC.E > TGT.E
THEN UPDATE SET TGT.E = SRC.E
WHEN NOT MATCHED BY TARGET
THEN INSERT VALUES (SRC.A, SRC.B, SRC.C, SRC.D, SRC.E)