Oracle
 sql >> Datenbank >  >> RDS >> Oracle

Verschachtelte Oracle SQL-Beziehung in einer Ebene

Ich bin mir nicht sicher, ob ich die Logik, die Sie zu implementieren versuchen, vollständig verstehe, aber hier ist SQL, das Ihre Tabelle erstellt und Ihre Beispielausgabe dupliziert. Es wurde auf https://livesql.oracle.com getestet

Bitte nehmen Sie dies mit Vorsicht, denn wenn Ihre Daten möglicherweise doppelte Zeilen oder Zyklen oder ähnliches enthalten, was in Ihrem Beispiel nicht gezeigt wird, muss die Abfrage möglicherweise geändert werden.

Gliederung:

  1. In der „with“-Klausel schwenken wir „ColumnA“ und „ColumnB“ in eine einzelne Spalte und fügen col_src hinzu, um zu bewahren, welche die neue „ColumnAB“ ist.

  2. Dann fragen wir rekursiv ab und verbinden durch eine übereinstimmende Spalte D und eine Spalte A/B, die mit der vorherigen Spalte C übereinstimmt.

  3. Um der bereitgestellten Reihenfolge zu entsprechen, sortieren wir nach:

    • die Rekursionsebene
    • Spalte C
    • ob die Quelle Spalte A oder B war
    • der Wert der Spalte A oder B
create table mytable as
select 'A' "ColumnA",'B' "ColumnB",'C' "ColumnC",'E' "ColumnD" from dual
union select 'D' "ColumnA",'C' "ColumnB",'F' "ColumnC",'E' "ColumnD" from dual
union select 'C' "ColumnA",'H' "ColumnB",'I' "ColumnC",'E' "ColumnD" from dual
union select 'C' "ColumnA",'W' "ColumnB",'S' "ColumnC",'E1' "ColumnD" from dual
;

with temp as (
    select "ColumnA" as "ColumnAB", "ColumnC", "ColumnD", 'A' as col_src
    from mytable
    union all select "ColumnB", "ColumnC", "ColumnD", 'B' as col_src
    from mytable
)
select connect_by_root("ColumnAB") "ColumnV", "ColumnC" as "ColumnW" from temp
connect by prior "ColumnD" = "ColumnD" and prior "ColumnC" = "ColumnAB"
order by level,"ColumnC",col_src,  "ColumnAB"