2016-05-31 59 views
2

我嘗試執行此交易:合併在SQLSERVER - 不正確的語法

GO 
BEGIN TRAN; 
MERGE A AS t 
USING B AS tmp 
ON (t.domain = tmp.domain and t.link=tmp.link) 
WHEN NOT MATCHED BY A 
    THEN INSERT(ipVal, domain, dateStart, dateUpdate, dateFinish, link) VALUES(tmp.ipVal, tmp.domain, tmp.dateStart, tmp.dateUpdate, tmp.dateFinish, tmp.link) 
WHEN MATCHED 
    THEN UPDATE SET t.dateupdate = tmp.dateupdate 
WHEN NOT MATCHED BY B 
    THEN UPDATE SET t.datefinish="a" 
ROLLBACK TRAN; 
GO 

我把這個代碼here,但是,當我試圖執行這個,我得到了一個錯誤:

Incorrect syntax near 'A' 

什麼可以是問題嗎?

+0

一個可以理解的錯誤,因爲在TechNet頁面鏈接到您的用途'Target'和'Source'作爲例如表名,從而與'TARGET'和'SOURCE'關鍵字將它們混合。 – Heinzi

回答

6

根據MSDNWHEN NOT MATCHED爲分支的簡化語法是

[ WHEN NOT MATCHED [ BY TARGET ] [...] 
     THEN <merge_not_matched> ] 
    [ WHEN NOT MATCHED BY SOURCE [...] 
     THEN <merge_matched> ] [ ...n ] 

溶液與WHEN NOT MATCHED BY TARGETWHEN NOT MATCHED BY BWHEN NOT MATCHED BY SOURCE取代WHEN NOT MATCHED BY A

TARGETSOURCE是不是佔位符的T-SQL關鍵字。

0

一個我剛開始用MERGE我用這個語法的理解對不對:

MERGE A AS target 
USING B AS source 
ON (target.domain = source.domain and target.link=source.link) 
WHEN NOT MATCHED BY TARGET 
    THEN INSERT(ipVal, domain, dateStart, dateUpdate, dateFinish, link) 
    VALUES(source.ipVal, source.domain, source.dateStart, source.dateUpdate, source.dateFinish, source.link) 
WHEN MATCHED 
    THEN UPDATE SET target.dateupdate = source.dateupdate 
WHEN NOT MATCHED BY SOURCE 
    THEN UPDATE SET target.datefinish="a" 

我知道這是一個不好的做法,但開始的時候 - 有很大幫助。

由於@BogdanSahlean點TARGETSOURCE是關鍵字,當您確定匹配/不匹配的語句時需要。

0

看起來你正在試圖用char或varchar類型的數據更新日期或日期時間類型列,這些數據不可轉換爲日期或日期時間類型。 'a'不能轉換爲日期或日期時間。查看下面的第一個和第二個合併。如果您沒有提及何時匹配或何時不匹配源或目標,默認情況下它會考慮Target。

--DROP TABLE #A; 
--DROP TABLE #B; 

CREATE TABLE #A 
    (
     ipval VARCHAR(50) 
    , domain CHAR(5) 
    , dateStart DATE 
    , dateUpdate DATE 
    , dateFinish DATE 
    , link VARCHAR(50) 
    ); 

CREATE TABLE #B 
    (
     ipval VARCHAR(50) 
    , domain CHAR(5) 
    , dateStart DATE 
    , dateUpdate DATE 
    , dateFinish DATE 
    , link VARCHAR(50) 
    ); 
INSERT INTO #B 
     (ipval, domain, dateStart, dateUpdate, dateFinish, link) 
VALUES ('42.130.239.56' -- ipval - varchar(50) 
      , '.com' -- domain - char(5) 
      , GETDATE() -- dateStart - date 
      , DATEADD(DAY, 1, GETDATE()) -- dateUpdate - date 
      , DATEADD(DAY, 5, GETDATE()) -- dateFinish - date 
      , 'www.stackoverflow' -- link - varchar(50) 
      ), 
     ('78.188.136.74' -- ipval - varchar(50) 
      , '.com' -- domain - char(5) 
      , GETDATE() -- dateStart - date 
      , DATEADD(DAY, 2, GETDATE()) -- dateUpdate - date 
      , DATEADD(DAY, 10, GETDATE()) -- dateFinish - date 
      , 'www.msdn' -- link - varchar(50) 
      ); 

INSERT INTO #A 
     (ipval, domain, dateStart, dateUpdate, dateFinish, link) 
VALUES ('30.48.111.20' -- ipval - varchar(50) 
      , '.com' -- domain - char(5) 
      , GETDATE() -- dateStart - date 
      , DATEADD(DAY, 5, GETDATE()) -- dateUpdate - date 
      , DATEADD(DAY, 10, GETDATE()) -- dateFinish - date 
      , 'www.msdn' -- link - varchar(50) 
      ), 
     ('30.48.111.20' -- ipval - varchar(50) 
      , '.com' -- domain - char(5) 
      , GETDATE() -- dateStart - date 
      , DATEADD(DAY, 5, GETDATE()) -- dateUpdate - date 
      , DATEADD(DAY, 10, GETDATE()) -- dateFinish - date 
      , 'www.gmail' -- link - varchar(50) 
      ); 
--First Merge 
BEGIN TRAN; 
MERGE #A AS T 
USING #B AS tmp 
ON T.domain = tmp.domain 
    AND T.link = tmp.link 
WHEN NOT MATCHED BY TARGET THEN 
    INSERT (ipval 
      , domain 
      , dateStart 
      , dateUpdate 
      , dateFinish 
      , link 
      ) 
    VALUES (tmp.ipval 
      , tmp.domain 
      , tmp.dateStart 
      , tmp.dateUpdate 
      , tmp.dateFinish 
      , tmp.link 
      ) 
WHEN MATCHED THEN 
    UPDATE SET T.dateUpdate = tmp.dateUpdate 
WHEN NOT MATCHED BY SOURCE THEN 
    UPDATE SET T.dateFinish =''a''; 
COMMIT TRAN; 
GO 


SELECT * 
FROM #A; 
SELECT * 
FROM #B; 
--Second Merge 
BEGIN TRAN; 
MERGE #A AS T 
USING #B AS tmp 
ON T.domain = tmp.domain 
    AND T.link = tmp.link 
WHEN NOT MATCHED BY TARGET THEN 
    INSERT (ipval 
      , domain 
      , dateStart 
      , dateUpdate 
      , dateFinish 
      , link 
      ) 
    VALUES (tmp.ipval 
      , tmp.domain 
      , tmp.dateStart 
      , tmp.dateUpdate 
      , tmp.dateFinish 
      , tmp.link 
      ) 
WHEN MATCHED THEN 
    UPDATE SET T.dateUpdate = tmp.dateUpdate 
WHEN NOT MATCHED BY SOURCE THEN 
    UPDATE SET T.dateFinish = CAST(GETDATE() AS DATE); 
COMMIT TRAN; 
GO 


SELECT * 
FROM #A; 
SELECT * 
FROM #B;