Frage

Wie berechne ich die Tiefe eines Knotens in einem Eltern-Kind-Modell unter MySQL?

Ich brauche die Tiefe, um unter anderem den Einzug in meiner Liste zu erstellen (codiert mit PHP).

War es hilfreich?

Lösung 2

Dies mag eine alte Frage sein, aber ich möchte nur andere wissen lassen, dass ich vor einigen Monaten eine Lösung gefunden habe. Ich habe kürzlich hier darüber geschrieben: http://en.someotherdeveloper.com/articles/adjaca-list-model-withdepth-calculation/

Andere Tipps

Dies hängt von der tatsächlichen Implementierung Ihrer Hierarchie in der Datenbank ab. Wenn Sie verschachtelte Sets Modell verwenden (http://mikehillyer.com/articles/managing-hierarchical-data-in-mysql/) Sie können den vollständigen Eltern-zu-Kind-Pfad über einen einzelnen Auswahlpfad abrufen.

Aktualisieren: OK, da Sie mit dem Adjazency List -Modell eingehen, empfehle ich, die Knotenebene in der Tabelle zu speichern. Es gibt Ihnen nicht nur die Knotentiefe in einer Abfrage, sondern ermöglicht es Ihnen auch, den gesamten Pfad zu diesem Knoten in einer Abfrage abzurufen (obwohl die Abfrage dynamisch generiert werden müsste):

SELECT n1.name AS lvl1, n2.name as lvl2, n3.name as lvl3, ..., nN.name as lvlN
  FROM nodes AS n1
  JOIN nodes AS n2 ON n2.parent_id = n1.id
  JOIN nodes AS n3 ON n3.parent_id = n2.id
  ...
  JOIN nodes AS nN ON nN.parent_id = n(N-1).id
WHERE nN.id = myChildNode;

Da Sie wissen, dass sich Ihr Knoten auf Level N befindet, sind keine linken Verknüpfungen erforderlich, und angesichts der entsprechenden Indizes für ID / parent_id sollte dies einigermaßen schnell sein.
Der Nachteil dieses Ansatzes besteht darin, dass Sie die Knotenebene während der Knotenbewegungen auf dem Laufenden halten müssen, aber dies sollte einigermaßen einfach und schnell sein, wie Sie es nur für den Knoten selbst und seine Kinder tun würden - nicht für den größten Teil des Tisches als Sie würden es mit verschachtelten Sets machen.

Wenn Sie hier nur Einfügen kopieren möchten, ist mein Beispiel. Ich habe Tabellenprojekte mit ID und Eltern_ID -Abstellungen.

DELIMITER $$
DROP FUNCTION IF EXISTS `getDepth` $$
CREATE FUNCTION `getDepth` (project_id INT) RETURNS int
BEGIN
    DECLARE depth INT;
    SET depth=1;

    WHILE project_id > 0 DO
        SELECT IFNULL(parent_id,-1) 
        INTO project_id 
        FROM ( SELECT parent_id FROM Projects WHERE id = project_id) t;

        IF project_id > 0 THEN
            SET depth = depth + 1;
        END IF;

    END WHILE;

    RETURN depth;

END $$
DELIMITER ;
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top