Rolf B: Vorfahren aus Datenbank rekursiv ermitteln?

Beitrag lesen

Hallo Linuchs,

Meine DB ist MySQL-Vers.=[10.1.37-MariaDB-0+deb9u1

welches DBMS, welche Version genau? Hab ich Dich bestimmt schon 17 mal gefragt, aber ich habe kein Dossier für jeden Forenteilnehmer 😉. Und ein schlechtes Gedächtnis.

Das geht mit rekursiven Common Table Expressions. Du musst auf Maria 10.2 oder höher updaten, damit die möglich sind.

Ohne rekursive CTE bleibt Dir nur die Joinerei - oder Du musst pro Generation eine neue Query starten und jeweils die Liste der Eltern-IDs aus der vorigen Generation als IN-Klausel reingeben.

Was sollen übrigens die varchars für Vater und Mutter? Soll das eine Alternative sein für den Fall, dass Du die Eltern nur namentlich hast, aber nicht als Person mit ID?

Damit Du weißt, was Dich erwartet: die Query mit rekursiven CTEs sieht in MariaDB so aus. Sie ist eeeetwas komplizierter, weil Du zwei CTEs brauchst und die Ergebnisse kombinieren musst, einmal in Elternrichtung und einmal in Kinderrichtung. Andernfalls gibt's eine Endlosschleife (zumindest bei mir gerade, in einer Testtabelle).

Die magische Zahl 4, die da an 3 Stellen auftaucht, ist die ID der Bezugsperson, hier im Beispiel Herzog Max in Bayern.

WITH RECURSIVE 
   Eltern (stufe, id, vater_id, mutter_id,
           vor_name, geb_name, geb_datum, sterbe_datum) 
   AS (
      SELECT 0 AS stufe, id, vater_id, mutter_id,
             vor_name, geb_name, geb_datum, sterbe_datum
      FROM stammbaum
      WHERE id=4
     UNION ALL
      SELECT e.stufe-1, s.id, s.vater_id, s.mutter_id,
             s.vor_name, s.geb_name, s.geb_datum, s.sterbe_datum
      FROM stammbaum s JOIN Eltern e
           ON s.id = e.vater_id OR s.id = e.mutter_id
      WHERE e.stufe > -2
   ),
   Kinder (stufe, id, vater_id, mutter_id, 
           vor_name, geb_name, geb_datum, sterbe_datum) 
   AS (
       SELECT 1 AS stufe, id, vater_id, mutter_id,
              vor_name, geb_name, geb_datum, sterbe_datum
       FROM stammbaum
       WHERE vater_id = 4 OR mutter_id = 4
     UNION ALL
       SELECT k.stufe+1, s.id, s.vater_id, s.mutter_id,
             s.vor_name, s.geb_name, s.geb_datum, s.sterbe_datum
       FROM stammbaum s JOIN Kinder k
                         ON k.id = s.vater_id OR k.id = s.mutter_id
       WHERE k.stufe < 2
   )
SELECT * FROM Eltern
UNION 
SELECT * FROM Kinder
ORDER BY stufe

Damit krieg ich dann z.B. sowas raus:

Hab ich gerade den Stammbaum von Sissi in eine Table gekloppt? Ja. In der Tat 😂

Rolf

--
sumpsi - posui - obstruxi