SQL Server - 更新列,其中<set of =“”columns =“”>不在<another table =“”> </other> </set>

时间:2012-06-15 15:38:39

标签: sql-server

假设我有两个表MainOther,如下所示:

                    Main
+----------+-----------------------------------+
|  Field1  |  <set of other columns...>        |
+----------+-----------------------------------+
|   NULL   |           ...                     |
|   NULL   |           ...                     |
|   NULL   |           ...                     |


                          Other
           +-----------------------------------+
           |  <same set of other columns...>   |
           +-----------------------------------+
           |           ...                     |
           |           ...                     |
           |           ...                     |

是否有一种简洁的方式来更新Main.Field1,其余列一起排在Other行?

换句话说,我想为

中的每一行更新Field1
SELECT <set of other columns...> FROM Main
   EXCEPT
SELECT <same set of other columns...> FROM Other

动态SQL是一个选项,但我试图找出最有效的方法来做这样的事情。

2 个答案:

答案 0 :(得分:1)

update m
set ...
from Main m
where not exists(select * from Other where <columns-equal>)

这转换为左反半连接。

您也可以使用左连接但转换为普通的左连接加滤波器,效率稍低。这看起来像是优化者的弱点。

答案 1 :(得分:1)

如果你真的想要,你可以使用Except子句

UPDATE m
SET field = 'AValue'
FROM 
   MAIN  m
   INNER JOIN 
    (SELECT * FROM MAIN
    EXCEPT
    SELECT * FROM OTHER ) t
on m.PK = t.PK

DEMO

您应该注意,此处*的使用非常脆弱,您应该明确设置字段列表。它还假设连接字段(PK)在Main和Other中都可用,它们将是相同的

另外,你使用NOT EXISTS或ANTI-JOIN(LEFT / ISNULL)会好得多吗

UPDATE m
   SET Field1 = 'foo'
FROM 
   Main m
   LEFT JOIN 
     Other o
    ON m.FIELD2 = o.FIELD2
    AND m.FIELD3 = o.FIELD3
WHERE 
   o.PK is null

DEMO