I need to merge overlapping periods (defined by FROM and TO variables) of sequential events (with identifier NUM) for each group (ID) with a \"lookahead buffer\", meaning that i
You should use the RESET WHEN
window modifier in your analytic functions (LAG
in Teradata 16, or MAX
in earlier ones); don't use a recursive query.
Update:
DROP TABLE MY_TABLE;
CREATE VOLATILE TABLE MY_TABLE
( id INTEGER
, num INTEGER
, from_value INTEGER
, to_value INTEGER
, lookahead INTEGER
) ON COMMIT PRESERVE ROWS;
INSERT INTO MY_TABLE VALUES (1, 1, 1, 10, 5);
INSERT INTO MY_TABLE VALUES (1, 2, 13, 20, 5);
INSERT INTO MY_TABLE VALUES (1, 3, 21, 25, 3);
INSERT INTO MY_TABLE VALUES (1, 4, 29, 31, 3);
INSERT INTO MY_TABLE VALUES (1, 5, 40, 50, 3);
INSERT INTO MY_TABLE VALUES (2, 1, 1, 10, 5);
INSERT INTO MY_TABLE VALUES (2, 2, 20, 30, 15);
INSERT INTO MY_TABLE VALUES (2, 3, 40, 41, 5);
INSERT INTO MY_TABLE VALUES (2, 4, 100, 200, 5);
INSERT INTO MY_TABLE VALUES (2, 5, 300, 400, 3);
SELECT id, first_from_value, to_value
FROM ( SELECT id
, to_value
, CASE WHEN overlaps_flag = 1
THEN NULL
ELSE COALESCE
( MIN (from_value)
OVER (PARTITION BY id
ORDER BY from_value
RESET WHEN MAX (overlaps_flag)
OVER (PARTITION BY id
ROWS BETWEEN
1 PRECEDING
AND 1 PRECEDING) = 0
ROWS BETWEEN UNBOUNDED PRECEDING
AND 1 PRECEDING)
, from_value )
END AS first_from_value
FROM ( SELECT id, from_value, to_value
, MAX (from_value)
OVER (PARTITION BY id
ORDER BY from_value
ROWS BETWEEN 1 FOLLOWING AND 1 FOLLOWING)
AS next_from_value
, CASE WHEN to_value + lookahead + 1 >= next_from_value
THEN 1 ELSE 0
END AS overlaps_flag
FROM my_table
) AS a
) AS a
WHERE first_from_value IS NOT NULL
ORDER BY 1, 2
id first_from_value to_value
1 1 31
1 40 50
2 1 10
2 20 41
2 100 200
2 300 400