WITH TMP AS (SELECT 1 AS ID, NULL AS PARENT_ID FROM DUAL
UNION
SELECT 2 AS ID, 1 AS PARENT_ID FROM DUAL
UNION
SELECT 3 AS ID, 2 AS PARENT_ID FROM DUAL
UNION
SELECT 4 AS ID, 3 AS PARENT_ID FROM DUAL
UNION
SELECT 5 AS ID, 3 AS PARENT_ID FROM DUAL
UNION
SELECT 6 AS ID, 2 AS PARENT_ID FROM DUAL
UNION
SELECT 7 AS ID, 1 AS PARENT_ID FROM DUAL
UNION
SELECT 8 AS ID, NULL AS PARENT_ID FROM DUAL
UNION
SELECT 9 AS ID, 8 AS PARENT_ID FROM DUAL
UNION
SELECT 10 AS ID, 8 AS PARENT_ID FROM DUAL
UNION
SELECT 11 AS ID, 10 AS PARENT_ID FROM DUAL
UNION
SELECT 12 AS ID, NULL AS PARENT_ID FROM DUAL
UNION
SELECT 13 AS ID, 12 AS PARENT_ID FROM DUAL
UNION
SELECT 14 AS ID, NULL AS PARENT_ID FROM DUAL),
LVL_BREAKDOWN
AS (SELECT LVL,
ID_PATH,
TO_NUMBER (REGEXP_SUBSTR (ID_PATH,
'[^/]+',
1,
1))
LEVEL1,
TO_NUMBER (REGEXP_SUBSTR (ID_PATH,
'[^/]+',
1,
2))
LEVEL2,
TO_NUMBER (REGEXP_SUBSTR (ID_PATH,
'[^/]+',
1,
3))
LEVEL3,
TO_NUMBER (REGEXP_SUBSTR (ID_PATH,
'[^/]+',
1,
4))
LEVEL4
FROM ( SELECT LEVEL AS LVL,
SYS_CONNECT_BY_PATH (ID, '/') ID_PATH
FROM TMP
START WITH PARENT_ID IS NULL
CONNECT BY PRIOR ID = PARENT_ID))
SELECT LB1.*
FROM LVL_BREAKDOWN LB1
WHERE lvl = 4
UNION
SELECT LB1.*
FROM LVL_BREAKDOWN LB1
WHERE lvl = 3
AND NOT EXISTS
(SELECT 'x'
FROM LVL_BREAKDOWN LB2
WHERE LB1.LEVEL1 = LB2.LEVEL1
AND LB1.LEVEL2 = LB2.LEVEL2
AND LB1.LEVEL3 = LB2.LEVEL3
AND lvl = 4)
UNION
SELECT LB1.*
FROM LVL_BREAKDOWN LB1
WHERE lvl = 2
AND NOT EXISTS
(SELECT 'x'
FROM LVL_BREAKDOWN LB2
WHERE LB1.LEVEL1 = LB2.LEVEL1
AND LB1.LEVEL2 = LB2.LEVEL2
AND lvl = 3)
UNION
SELECT LB1.*
FROM LVL_BREAKDOWN LB1
WHERE lvl = 1
AND NOT EXISTS (SELECT 'x'
FROM LVL_BREAKDOWN LB2
WHERE LB1.LEVEL1 = LB2.LEVEL1 AND lvl = 2)
ORDER BY 3, 4 ASC
LVL | ID_PATH | LEVEL1 | LEVEL2 | LEVEL3 | LEVEL4 | 3 | /1/2/6 | 1 | 2 | 6 | - | 4 | /1/2/3/4 | 1 | 2 | 3 | 4 | 4 | /1/2/3/5 | 1 | 2 | 3 | 5 | 2 | /1/7 | 1 | 7 | - | - | 2 | /8/9 | 8 | 9 | - | - | 3 | /8/10/11 | 8 | 10 | 11 | - | 2 | /12/13 | 12 | 13 | - | - | 1 | /14 | 14 | - | - | - |
---|