我试图加载标准金博尔SCD2尺寸,利用我从以下网站获得了合并声明: http://www.kimballgroup.com/2008/11/design-tip-107-using-the-sql-merge-statement-for-slowly-changing-dimension-processing/MERGE试图更新或删除同一行不止一次
此合并声明除了处理新的实体相同之外。这将作为数据流中的直接插入来处理。此问题仅涉及同一业务密钥的多个版本。
当我执行MERGE语句SQL返回错误:
Msg 8672, Level 16, State 1, Line 3
The MERGE statement attempted to UPDATE or DELETE the same row more than once. This happens when a target row matches more than one source row.
A MERGE statement cannot UPDATE/DELETE the same row of the target table multiple times. Refine the ON clause to ensure a target row matches at most one source row, or use the GROUP BY clause to group the source rows.
我使用SQL Server 2012:
SOURCE DATASET
目标数据集
这是我所期待的:
下面你可以找到脚本来重现问题:
CREATE TABLE SANDBOX.EHN.SOURCE_SCD2 (
BUSINESS_KEY BIGINT
,DESCRIPTION_A VARCHAR(2)
,M_CRC BIGINT
,StartDATE DATE
,EndDATE DATE)
CREATE TABLE SANDBOX.EHN.TARGET_SCD2 (
BUSINESS_KEY BIGINT
,DESCRIPTION_A VARCHAR(2)
,M_CRC BIGINT
,StartDATE DATE
,EndDATE DATE)
select *
from SANDBOX.EHN.TARGET_SCD2
truncate table SANDBOX.EHN.TARGET_SCD2
INSERT INTO SANDBOX.EHN.SOURCE_SCD2 VALUES (1, 'B', 1, '2015-05-16', '2015-06-01')
INSERT INTO SANDBOX.EHN.SOURCE_SCD2 VALUES (1, 'C', 2, '2015-06-01', '2015-06-11')
INSERT INTO SANDBOX.EHN.SOURCE_SCD2 VALUES (1, 'D', 3, '2015-06-11', '9999-12-31')
INSERT INTO SANDBOX.EHN.TARGET_SCD2 VALUES (1, 'A', 0, '2015-01-16', '9999-12-31')
INSERT INTO SANDBOX.EHN.TARGET_SCD2
SELECT BUSINESS_KEY
,DESCRIPTION_A
,M_CRC
,StartDATE
,EndDATE
FROM (
MERGE SANDBOX.EHN.TARGET_SCD2 D
USING SANDBOX.EHN.SOURCE_SCD2 UPD
ON(D.BUSINESS_KEY = UPD.BUSINESS_KEY)
WHEN MATCHED AND D.EndDATE = '9999-12-31'
THEN UPDATE SET D.EndDATE = UPD.EndDATE
OUTPUT $Action Action_Out, UPD.BUSINESS_KEY
, UPD.DESCRIPTION_A
, UPD.M_CRC
, UPD.StartDATE
, UPD.EndDATE
)AS MERGE_OUT
WHERE MERGE_OUT.Action_Out = 'UPDATE'
你能不能帮我解决这个问题?
那么,错误消息是相当明确的:你有一个目标行,合并语句试图更新或删除多次。这不适用于合并声明。重写您的查询以确保一行只能是一个更新或删除语句的目标。 –
谢谢你的回复,但这正是问题所在,我们知道'我们需要做什么,但不知道'如何'? –
我有点困惑... AFAICT MERGE语句是顶级语句,不能像你在做的那样在派生表中使用。至少我没有在[documentation](https://msdn.microsoft.com/en-us/library/bb510625.aspx)中看到这种可能的用法。我在测试数据库(SS 2012)上执行了脚本,它给出了一个错误消息,我认为这是由于这个事实(*在包含合并的派生表的开始处,'D'*附近有错误的语法)。我错过了什么吗? –