2017-05-10 31 views
0

我在Oracle SQL数据库中有两个表。感兴趣的领域是:从另一个表中匹配数据和字段的Oracle SQL UPDATE查询

表A: 参考-A | Type-A |时间戳-A

表B: 参考-B | Type-B |时间戳-B

在表B中的时间戳字段是新创建,并因此所有NULL,我想要更新该字段与从表A的时间戳值

参考-A和参考-B做匹配一对一,但是对于每个不同类型的引用有多行,所以我也需要选择类型。 Type-A和Type-B并不相同,所以我需要对它们进行IF-ELSE匹配,例如:Type-B1-> Type-A1,Type-B2-> Type-A2

并不是所有的Reference-B和Type-B的组合在表A中都有匹配,所以对于这些情况,它可以将表B中的时间戳设置为空。

那么这个UPDATE语句的SQL查询是怎么样的呢?我试过这个(伪);

UPDATE B 
SET timestamp = (
    SELECT A.timestamp 
    FROM A, B 
    WHERE A.reference = B.reference 
     AND A.type = 
     (CASE 
      WHEN B.type = 'B1' 
      THEN 'A1' 
      WHEN B.type = 'B2' 
      THEN 'A2' 
      WHEN B.type = 'B3' 
      THEN 'A3' 
      WHEN B.type = 'B4' 
      THEN 'A4' 
     END) 
); 

但是当我运行此查询,我得到以下错误:“SQL错误:ORA-01427:单行子查询返回多个行”。

任何想法?

+0

尝试在SELECT查询中使用DISTINCT。 – user75ponic

+0

那个错误意味着你的子查询返回多于一行至少一组a.reference和a.type。如果子查询匹配多个时间戳,你需要决定子查询应该返回什么 - 它是否应该返回最新或最早的时间戳(最大/最小)?随机时间戳('rownum = 1')?只有你知道你的数据和你的要求,所以只有你可以决定... – Boneist

回答

0
UPDATE B 
SET timestamp = (
    SELECT A.timestamp 
    FROM A 
    WHERE A.reference = B.reference 
     AND A.type = 
     (CASE 
      WHEN B.type = 'B1' 
      THEN 'A1' 
      WHEN B.type = 'B2' 
      THEN 'A2' 
      WHEN B.type = 'B3' 
      THEN 'A3' 
      WHEN B.type = 'B4' 
      THEN 'A4' 
     END) 
     AND rownum < 2 -- !!! select only 1 row 
); 
0

如错误消息中所示,您的子查询返回多个行。在子查询中,您不需要再次连接表B.如果表参考A和参考B确实匹配一对一,则可以像这样更新您的查询

UPDATE B 
SET timestamp = (
    SELECT A.timestamp 
    FROM A 
    WHERE A.reference = B.reference 
     AND A.type = 
     (CASE 
      WHEN B.type = 'B1' 
      THEN 'A1' 
      WHEN B.type = 'B2' 
      THEN 'A2' 
      WHEN B.type = 'B3' 
      THEN 'A3' 
      WHEN B.type = 'B4' 
      THEN 'A4' 
     END) 
); 
相关问题