Question

Je suis en train de chercher un arbre généalogique des animaux de ma base de données Oracle.

Voici le tableau:

Animal
------------------------
Animal_ID
Parent_Male_ID
Parent_Female_ID
....
....
------------------------

Si je précise un animal, je peux obtenir tous ses descendants (sur le côté mâle) en utilisant quelque chose comme ceci:

SELECT *
FROM animal
START WITH animal_id = 123
CONNECT BY PRIOR animal_id = parent_male_id

Je suis en train de trouver un moyen d'étendre ceci de telle sorte que si un animal je précise, il va chercher les deux parents et va chercher tous leurs descendants.

Toutes les pensées? (Ce qui est Oracle 9.2)

Était-ce utile?

La solution

SELECT  *
FROM    animal
START WITH
        animal_id IN
        (
        SELECT  parent_male_id
        FROM    animal
        WHERE   animal_id = 123
        UNION ALL 
        SELECT  parent_female_id
        FROM    animal
        WHERE   animal_id = 123
        )
CONNECT BY
        PRIOR animal_id IN (parent_male_id, parent_female_id)

Cette requête, cependant, sera assez lent.

Il vaut mieux utiliser celui-ci:

SELECT  DISTINCT(animal_id) AS animal_id
FROM    (
        SELECT  0 AS gender, animal_id, father AS parent
        FROM    animal
        UNION ALL
        SELECT  1, animal_id, mother
        FROM    animal
        )
START WITH
        animal_id IN
        (
        SELECT  father
        FROM    animal
        WHERE   animal_id = 9500
        UNION ALL 
        SELECT  mother
        FROM    animal
        WHERE   animal_id = 9500
        )
CONNECT BY
        parent = PRIOR animal_id
ORDER BY
        animal_id

, qui utilisera HASH JOIN et est beaucoup plus rapide.

Voir cette entrée dans mon blog pour les détails de la performance:

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top