更新oracle表引用更新的表/字段? (相关更新?)

时间:2017-05-11 11:25:09

标签: sql oracle correlated-subquery

我有一个任务管理器,它会在日志表中删除一些与此类似的信息:

processId    owner      state            state_date
------------------------------------------------------------

1-88D6PJ     group1     OPENED           14/08/2013 14:57:44
1-88D6PJ     group2     ASSIGNED         14/08/2013 14:58:36
1-88D6PJ     group3     ASSIGNED         15/08/2013 11:26:45
1-88D6PJ     group2     ASSIGNED         17/08/2013 17:20:13
1-88D6PJ     group3     ASSIGNED         19/08/2013 09:05:12
1-88D6PJ     null       FINISHED         22/08/2013 12:13:59

任务完成后,不会存储所有者。在代码中修复它,但现在我想修复旧条目。

要做到这一点,对于每个拥有null所有者的条目,我需要搜索倒数第二个条目以获取所有者,这将是关闭任务的人。

我试图做一个方法,似乎与此类似的东西可以起作用:

UPDATE tasks.tasks_log t1
   set (t1.owner) =
       (SELECT owner
          FROM (SELECT owner
                  FROM tasks.tasks_log t2
                 WHERE t1.processId = ep2.processId
                   and state not in ('FINISHED', 'CANCELLED')
                   and state_date is not null
                 ORDER BY state_date DESC)
         WHERE rownum = 1)

可能不优雅或有效,但似乎它可以工作,但是当我运行它时,我会收到一个ORA-00904:" t1"。" processId"无效的标识符。

我假设不可能引用更新的表标识符,但在检查了oracle文档和一些帖子之后,我看到similar UPDATES被禁止工作。

有可能作出参考吗?或者我必须完全改变进行此更新的方法?

1 个答案:

答案 0 :(得分:1)

有几种方法可以做到这一点(例如merge)。但是根据您的方法,您可以使用keep

UPDATE tasks.tasks_log t1
   set (t1.owner) = (SELECT MAX(t2.owner) KEEP (FIRST DENSE_RANK ORDER BY BY state_date DESC)
                     FROM tasks.tasks_log t2
                     WHERE t1.processId = ep2.processId AND
                           t2.state not in ('FINISHED', 'CANCELLED') AND
                           t2.state_date is not null
                    );