Postgres在一个动作中更新多行

时间:2015-09-02 08:30:01

标签: sql postgresql sql-update

我有两张桌子

app_detail_quot_s
-----------+--------------+
part_id    +unit_price    +
-----------+--------------+
1          +    100.000   +
2          +    200.000   +
3          +    300.000   +


app_supp_po_dt
-----------+--------------+
part_id    +unit_price    +
-----------+--------------+
1          +    null      +
2          +    null      +
8          +    null      +

执行查询更新后的结果是

app_supp_po_dt
-----------+--------------+
part_id    +unit_price    +
-----------+--------------+
1          +    100.000   +
2          +    200.000   +
8          +    null      +

如果使用PostgreSQL在unit_pricepart_id之间的app_detail_quots在一个操作中相等时,如何更新所有app_supp_po_detail

我正在尝试这段代码:

update app_supp_po_dt set
    unit_price =
 ( 
    select unit_price from app_detail_quot_s a left join app_supp_po_dt b on    a.part_id= b.part_id
 ) 

但我得到错误:

  

用作表达式

的子查询返回的多行

1 个答案:

答案 0 :(得分:1)

您不需要在子选择内部加入,只需将其作为常规的共同相关子选择:

update app_supp_po_dt 
 set unit_price = (select unit_price 
                   from app_detail_quot_s a 
                   where a.part_id = app_supp_po_dt.part_id);

以上假设part_id在两个表中都是唯一的。

如果在null中找不到part_id并且在这种情况下会覆盖app_detail_quot_s中存储的任何值,则共同相关的子查询将返回app_supp_po_dt,如果您不希望这样,您需要从app_supp_po_dt中排除具有单价但未显示在app_detail_quot_s

中的行
update app_supp_po_dt 
 set unit_price = ( select unit_price from app_detail_quot_s a where a.part_id = app_supp_po_dt.part_id)
where unit_price is null
  and exists (select 1 
              from app_detail_quot_s a2 
              where a2.part_id = app_supp_po_dt.part_id);

另一个(非标准)选项是在update语句中使用连接,这使得语句更具可读性:

update app_supp_po_dt 
  set unit_price = a.unit_price
from app_detail_quot_s a
where a.part_id = app_supp_po_dt.part_id;

这是非标准SQL,不适用于其他DBMS,但最有可能比具有共同相关子查询的解决方案快得多