web-dev-qa-db-ja.com

マージでWhere句を使用する

When Matchedを使用した以下の構文では、更新テーブルの値が従業員テーブルの値と異なる場合にのみ更新できますか?以下のDDLに似たもの-もちろんこれはエラーをスローし、機能しません。

構文を更新して、異なる行のみを更新する必要がありますか?目的の更新は、一致するすべての行を反復するのではなく、アドレスが異なるためemp44 & emp55のみを更新することです。

提示されたエラーは

メッセージ156、レベル15、状態1、行24
キーワード「WHERE」付近の構文が正しくありません。

構文

  DECLARE @Emp Table (empid varchar(10), empaddress varchar(100))
  Insert Into @Emp Values 
  ('emp11', '111 No Blue'), 
  ('emp22', '222 No Blue'),
  ('emp33', '333 No Blue'), 
  ('emp44', '444 No Blue'),
  ('emp55', '555 No Blue');

Declare @EmpUpdates TABLE (empid varchar(10), empaddress varchar(100))
Insert Into @EmpUpdates Values
('emp11', '111 No Blue'), 
('emp22', '222 No Blue'),
('emp33', '333 No Blue'), 
('emp44', '999 No Blue'),
('emp55', '888 No Blue'),
('emp66', '4141 No Blue');

MERGE @Emp emp
Using @EmpUpdates eup
ON emp.empid = eup.empid
 WHEN MATCHED THEN
UPDATE
SET emp.empaddress = eup.empaddress
WHERE emp.empaddress <> eup.empaddress
WHEN NOT MATCHED BY TARGET THEN
INSERT (empid, empaddress)
VALUES(eup.empid, eup.empaddress)
7

WHEREステートメントのその部分にはMERGEはありません。構文のヘルプについては、ドキュメントの MERGE (Transact-SQL) を参照してください。

WHEN MATCHED句にはオプションのAND部分があるため、簡単な答えはそこに条件を移動することです:

MERGE @Emp emp
USING @EmpUpdates eup
ON emp.empid = eup.empid
WHEN MATCHED 
     AND emp.empaddress <> eup.empaddress
  THEN
    UPDATE
    SET emp.empaddress = eup.empaddress
WHEN NOT MATCHED BY TARGET 
  THEN 
    INSERT (empid, empaddress)
    VALUES (eup.empid, eup.empaddress) ;

そこでヌルを正しく処理するように注意してください(empaddressがヌル可能である場合)。

トランザクションで2つの別々のステートメント(あなたの場合はUPDATEINSERT)で操作を実行する方がより明示的(かつ効率的)な場合があります。

また、これまでと同じように MERGEに関するいくつかの問題 があることに注意してください。

19
ypercubeᵀᴹ