【问题标题】:Oracle SQL - Update column data using MINUS operatorOracle SQL - 使用 MINUS 运算符更新列数据
【发布时间】:2022-01-02 06:52:03
【问题描述】:

我有这个 sql 查询

(select x.a, x.b, x.c, x.d
from tableX x
where x.a IS NOT NULL
minus 
select y.a, y.b, y.c, y.d
from tableY y);

上面的查询返回我所有的tableX数据,这与tableY不同。返回多个元组

证据:

当我运行上面的查询时,我得到这个结果:

a b c
1 43 65
2 66 333

当我从 tableY 中选择数据时,我得到了这个:

a b c
1 54 65
2 88 567

tableY 数据是正确的数据,所以我想用来自 tableY 的数据更新从第一个查询(带有 MINUS 子句的那个)返回的所有元组。

在更新子句之后,当我从 tableX 中选择数据时,预期的结果应该是:

a b c
1 54 65
2 88 567

执行此 UPDATE 子句最有效的方法是什么?

【问题讨论】:

  • 再添加几行样表数据,同时指定预期结果。
  • 我已经编辑了我的问题
  • 假设您的查询返回了第 (17, 54, 17) 行,那 tableX 行是否应该更新为 (1, 54, 65)?你怎么知道哪个 tableX 行更新到哪个 tableY 行?
  • “a”列为主键
  • where x.a IS NOT NULL 让我很困惑,因为主键不允许空值。

标签: sql oracle plsql


【解决方案1】:

在 oracle 上,我发现 MERGE 语法比 UPDATE 语法更有用...

MERGE INTO
  tablex   x
USING
  tabley   y
    ON (y.a = x.a)
WHEN MATCHED THEN UPDATE
  SET
    x.b = y.b,
    x.c = y.c
  WHERE
    LNNVL(x.b = y.b)
    OR
    LNNVL(x.c = y.c)

编辑:添加 where 子句以避免多余的更新,下面的评论。

【讨论】:

  • 交易中是否包含 x.b = y.b 和 x.c = y.c 的行?
  • @jarlh 在WHEN MATCHED 中添加了 where 子句以避免这种情况。
  • 这个解决方案解决了我的问题,谢谢
【解决方案2】:
update tablex
set (b, c) = (select b, c from tabley where tabley.a = tablex.a)
where exists (select 1 from tabley where tabley.a = tablex.a);

要减少交易大小,请添加 xb yb 或 xc yc:

update tablex
set (b, c) = (select b, c from tabley where tabley.a = tablex.a)
where exists (select 1 from tabley
              where tabley.a = tablex.a
                and (LNNVL(tabley.b = tablex.b) or LNNVL(tabley.c = tablex.c)));

【讨论】:

    猜你喜欢
    • 2019-10-07
    • 1970-01-01
    • 2012-02-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多