Oracle:Select 使用子查询中的复合键
Oracle: Select using compound key from subquery
情况是这样的——我们的记录使用 name/date 的复合键。我想查看所有连续执行了 2 个特定操作的名称,所以我想做类似
select name from
(select name as n, date as d from table where action='action1'),
(select name from table where name = n and date > d and action='action2' and rownum=1 order by date desc)
但它将 n 和 d 计为无效标识符。我怎样才能让它做我需要的事情?
一种方法可能是:
SELECT
a1.name
FROM
(SELECT name, date FROM table WHERE action = 'action1') a1
JOIN
(SELECT name, date FROM table WHERE action = 'action2') a2
ON
a2.name = a1.name
AND
a2.date > a1.date
如果一个名称的每个操作可以有多个实例,这可能会给您重复。在这种情况下,使用 SELECT DISTINCT
来消除重复可能就足够了。
请注意,这并不意味着这两个动作立即接连发生,只是说动作 2 在动作 1 之后的某个时间发生。
分析函数非常适合这类事情....免责声明这是快速而肮脏的,列名有点误导。 LAG/LEAD 是您想要玩的选项
http://sqlfiddle.com/#!4/bd7b2/7
select name,thedate,theaction,prev_action,prev_date from
(
select name,thedate,theaction,
lag(theaction) over (partition by name order by thedate,theaction) as prev_action,
lag(thedate) over (partition by name order by thedate,theaction) as prev_date
from table1
order by name,thedate,theaction
)
where theaction = 'action1' and prev_action = 'action2'
;
情况是这样的——我们的记录使用 name/date 的复合键。我想查看所有连续执行了 2 个特定操作的名称,所以我想做类似
select name from
(select name as n, date as d from table where action='action1'),
(select name from table where name = n and date > d and action='action2' and rownum=1 order by date desc)
但它将 n 和 d 计为无效标识符。我怎样才能让它做我需要的事情?
一种方法可能是:
SELECT
a1.name
FROM
(SELECT name, date FROM table WHERE action = 'action1') a1
JOIN
(SELECT name, date FROM table WHERE action = 'action2') a2
ON
a2.name = a1.name
AND
a2.date > a1.date
如果一个名称的每个操作可以有多个实例,这可能会给您重复。在这种情况下,使用 SELECT DISTINCT
来消除重复可能就足够了。
请注意,这并不意味着这两个动作立即接连发生,只是说动作 2 在动作 1 之后的某个时间发生。
分析函数非常适合这类事情....免责声明这是快速而肮脏的,列名有点误导。 LAG/LEAD 是您想要玩的选项
http://sqlfiddle.com/#!4/bd7b2/7
select name,thedate,theaction,prev_action,prev_date from
(
select name,thedate,theaction,
lag(theaction) over (partition by name order by thedate,theaction) as prev_action,
lag(thedate) over (partition by name order by thedate,theaction) as prev_date
from table1
order by name,thedate,theaction
)
where theaction = 'action1' and prev_action = 'action2'
;