Reputation: 133
I have a table with time periods like (no overlap in time periods):
start_date end_date
-----------------------------
12-aug-14 12-nov-14
12-jan-15 12-apr-15
12-jun-15 12-aug-15
... 5 more
I'm trying to find the in between time periods - something like:
12-nov-14 12-jan-15
12-apr-15 12-jun-15
...
However, my queries are giving all time period differences like:
12-nov-14 12-jan-15
12-nov-14 12-jun-15
My query was:
select
l1.end_date, l2.start_date
from
lease l1, lease l2
where
l1.place_no = 'P1' and l2.place_no = 'P1'
and l2.start_date > l1.end_date
order by
l1.end_date asc;
Any ideas?
Thanks!
Upvotes: 0
Views: 66
Reputation: 1269973
Use lead()
. That is what the function is designed for:
select l.*,
lead(start_date) over (partition by place_no order by start_date) as next_start_date,
(lead(start_date) over (partition by place_no order by start_date) as next_start_date - end_date) as gap
from lease l
where l1.place_no = 'P1';
There is no need for a join
or even for subqueries -- unless you want to eliminate the additional row that has a NULL value because there is no next value.
Upvotes: 2
Reputation: 7890
sort
your table, use rownum
and then join
them:
WITH CTE AS (
SELECT
START_DATE,
END_DATE,
ROWNUM AS RN
FROM ( SELECT START_DATE, END_DATE FROM TABLE_NAME ORDER BY 1,2)
)
SELECT T1.END_DATE, T2.START_DATE
FROM CTE T1 JOIN CTE T2 ON T2.RN=T1.RN+1
Upvotes: 1
Reputation: 9456
This is kind of tricky. You are currently creating a cartesian, which is close, after you create your cartesian, use a group-by to limit it back down to just the start-rows, and the minimum end-rows:
select
l1.end_date,
min(l2.start_date)
from
lease l1
inner join lease l2 ON
l1.place_no = l2.place_no and
l2.start_date >= l1 end_date
where
l1.place_no = 'P1'
group by
l1.start_date
having
l2.start_date != l1.end_date
Sorry about chaning your join syntax on you, it helps me organize my SQL better in my head.
Upvotes: 0