IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

SQL Oracle Discussion :

Jointure externe qui ne fonctionne pas


Sujet :

SQL Oracle

  1. #1
    Membre confirmé Avatar de juvamine
    Profil pro
    Chef de projet MOA
    Inscrit en
    Mai 2004
    Messages
    414
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations professionnelles :
    Activité : Chef de projet MOA
    Secteur : Agroalimentaire - Agriculture

    Informations forums :
    Inscription : Mai 2004
    Messages : 414
    Points : 502
    Points
    502
    Par défaut Jointure externe qui ne fonctionne pas
    Bonjour,

    J'ai un petit problème avec des jointures externe
    Rapidement, mon modèle: des lignes-commande (numéro_commande,ligne_commande,numero_facture), peuvent avoir zéro ou plusieurs commissions

    Si je fais une requete sans m'occuper des commissions:

    Code sql : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    SELECT   
      DWH_IND_CMD.NUM_CMD_PK,
      DWH_IND_CMD.NUM_LG_PK,
      sum(case when DWH_IND_CMD.TOP_BLOCAGE_FACT = '8' then DWH_IND_CMD.MT_CAN end)
    FROM
      DWH_IND_CMD,
      DWH_FACT,
      DWH_CLIENT,
      DWH_FAM_HIER_CLI,
      DWH_FAM_HIER_C_CLI
    WHERE
      ( DWH_CLIENT.CD_CLIENT_PK=DWH_IND_CMD.CD_CLI_FK and DWH_CLIENT.CD_FIL_PK=DWH_IND_CMD.CD_FIL_FK  )
      AND  ( DWH_CLIENT.CD_FAM_HIER_CLI_FK=DWH_FAM_HIER_CLI.CD_FAM_HIER_CLI_PK  )
      AND  ( DWH_FAM_HIER_CLI.CD_FAM_HIER_C_CLI_FK=DWH_FAM_HIER_C_CLI.CD_FAM_HIER_C_CLI_PK  )
      AND  ( DWH_IND_CMD.NUM_FACT_PK=DWH_FACT.NUM_FACT_PK(+)  )
      AND  (
      DWH_FAM_HIER_C_CLI.FAM_HIER_C_CLI  =  'GMS FRANCE'
      AND  ( DWH_FACT.DT_FACT BETWEEN to_date('01/03/2008') AND to_date('31/03/2008')  )
      )
    GROUP BY
      DWH_IND_CMD.NUM_CMD_PK, 
      DWH_IND_CMD.NUM_LG_PK
    me retourne 2990 lignes

    Si j'ajoute mes commissions:

    Code sql : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
     
    SELECT   
      DWH_IND_CMD.NUM_CMD_PK,
      DWH_IND_CMD.NUM_LG_PK,
      sum(case when DWH_IND_CMD.TOP_BLOCAGE_FACT = '8' then DWH_IND_CMD.MT_CAN end)
    FROM
      DWH_IND_CMD,
      DWH_FACT,
      DWH_CLIENT,
      DWH_FAM_HIER_CLI,
      DWH_FAM_HIER_C_CLI,
      DWH_AGENT,
      DWH_COMMISSION
    WHERE
      ( DWH_CLIENT.CD_CLIENT_PK=DWH_IND_CMD.CD_CLI_FK and DWH_CLIENT.CD_FIL_PK=DWH_IND_CMD.CD_FIL_FK  )
      AND  ( DWH_CLIENT.CD_FAM_HIER_CLI_FK=DWH_FAM_HIER_CLI.CD_FAM_HIER_CLI_PK  )
      AND  ( DWH_FAM_HIER_CLI.CD_FAM_HIER_C_CLI_FK=DWH_FAM_HIER_C_CLI.CD_FAM_HIER_C_CLI_PK  )
      AND  ( DWH_IND_CMD.NUM_FACT_PK=DWH_FACT.NUM_FACT_PK(+)  )
      AND  ( DWH_AGENT.CODE_AGENT=DWH_COMMISSION.NUM_AGENT_PK(+)  )
      AND  ( DWH_IND_CMD.NUM_CMD_PK(+)=DWH_COMMISSION.NUM_CMD_PK and DWH_IND_CMD.NUM_LG_PK(+)=DWH_COMMISSION.NUM_LG_PK and DWH_IND_CMD.NUM_FACT_PK(+)=DWH_COMMISSION.NUM_FACT_PK  )
      AND  (
      DWH_FAM_HIER_C_CLI.FAM_HIER_C_CLI  =  'GMS FRANCE'
      AND  ( DWH_FACT.DT_FACT BETWEEN to_date('01/03/2008') AND to_date('31/03/2008')  )
      )
    GROUP BY
      DWH_IND_CMD.NUM_CMD_PK, 
      DWH_IND_CMD.NUM_LG_PK;
    me retourne 2797 lignes

    j'ai beau retourner le problème dans tous les sens, il me manque toujours les lignes commande qui n'ont pas de commissions.

    si je fais requete A MINUS requete B, je retrouve bien ces lignes.

    Si quelqu'un peu m'aider...je suis preneur.

    A bientôt
    juva

  2. #2
    Modérateur
    Avatar de Waldar
    Homme Profil pro
    Sr. Specialist Solutions Architect @Databricks
    Inscrit en
    Septembre 2008
    Messages
    8 453
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 46
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Sr. Specialist Solutions Architect @Databricks
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2008
    Messages : 8 453
    Points : 18 394
    Points
    18 394
    Par défaut
    Vos (+) sont tout simplement du mauvais côté :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
      AND  ( DWH_AGENT.CODE_AGENT(+)=DWH_COMMISSION.NUM_AGENT_PK  )
      AND  ( DWH_IND_CMD.NUM_CMD_PK=DWH_COMMISSION.NUM_CMD_PK(+) AND DWH_IND_CMD.NUM_LG_PK = DWH_COMMISSION.NUM_LG_PK(+) AND DWH_IND_CMD.NUM_FACT_PK = DWH_COMMISSION.NUM_FACT_PK(+)  )

  3. #3
    Membre confirmé Avatar de juvamine
    Profil pro
    Chef de projet MOA
    Inscrit en
    Mai 2004
    Messages
    414
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations professionnelles :
    Activité : Chef de projet MOA
    Secteur : Agroalimentaire - Agriculture

    Informations forums :
    Inscription : Mai 2004
    Messages : 414
    Points : 502
    Points
    502
    Par défaut
    J'ai bien essayé mais c'est pareil

    et d'ailleur j'avais ce moyen mnémotechnique de me dire que le (+) devait se mettre du côté où on attendait le + de résultat.

    Bref j'avais essayé les 2 solutions et ça revient au même
    c'est comme si je changeais rien...

    j'ai déjà utiliser ce genre de chose, ça ne m'a jamais poser de problème. Mais là je tourne en rond

    Merci encore
    juva

  4. #4
    Modérateur
    Avatar de Waldar
    Homme Profil pro
    Sr. Specialist Solutions Architect @Databricks
    Inscrit en
    Septembre 2008
    Messages
    8 453
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 46
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Sr. Specialist Solutions Architect @Databricks
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2008
    Messages : 8 453
    Points : 18 394
    Points
    18 394
    Par défaut
    Avez-vous bien remarqué qu'il y avait deux jointures à modifier : entre AGENT et COMMISSION et entre COMMISSION et IND_CMD ?

    Quant à votre mnémotechnique, j'ai bien peur qu'il ne va vous falloir la reprendre.
    Les jointures externes ne sont pas une histoire de nombre, mais de population sur la clef de jointure.
    On met le (+) du côté où il y a un manque de population :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    WITH
        Personne AS
        (
        select 1 id, 'A' nom from dual union
        select 2, 'B' from dual union
        select 3, 'C' from dual
        ),
        Appels AS
        (
        select 1 id, '12:00:00' heure from dual union
        select 3, '15:00:00' from dual
        )
    select
        p.nom,
        count(distinct a.heure) nb_appels
    from
        Personne p,
        Appels a
    where
        p.id = a.id(+)
    group by     
        p.nom
    Quelques conseils sur votre requête :
    1) De l'air : utilisez des alias pour vos tables, limitez le nombre d'informations sur une ligne. C'est plus simple de naviguer de haut en bas que de haut en bas ET de gauche à droite.
    2) Utilisez la norme de jointure ANSI avec les LEFT JOIN. Ca élimine le doute sur le côté du (+)*
    3) Quand vous utilisez to_date (et to_char), mettez toujours un format !
    4) Le else dans le case, c'est bien aussi pour la relecture.

    *Je me rends bien compte que cette requête doit être générée avec un outil comme BO, mais parfois prendre le temps de réécrire la requête table par table dans votre outil SQL favori permet de retrouver ce genre d'erreur. Et les remarques 3 et 4 restent valables.

  5. #5
    Membre régulier
    Profil pro
    Inscrit en
    Septembre 2008
    Messages
    77
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Septembre 2008
    Messages : 77
    Points : 84
    Points
    84
    Par défaut
    Citation Envoyé par juvamine Voir le message
    J'ai bien essayé mais c'est pareil

    et d'ailleur j'avais ce moyen mnémotechnique de me dire que le (+) devait se mettre du côté où on attendait le + de résultat.
    Il y a une erreur dans ce moyen mnémotechnique. Le (+) se met du côté ou il y a le moins de records si tu veux employer ce principe. En fait, il se met du côté où il risque de te "manquer" des enregistrements.

    Je pense qu'il y a une erreur dans le select car les (+) ne sont pas toujours du même côté. Essayes en modifiant ceci:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    AND  ( DWH_AGENT.CODE_AGENT=DWH_COMMISSION.NUM_AGENT_PK(+)  )
    AND  ( DWH_IND_CMD.NUM_CMD_PK=DWH_COMMISSION.NUM_CMD_PK (+)
    AND DWH_IND_CMD.NUM_LG_PK=DWH_COMMISSION.NUM_LG_PK(+)
    AND DWH_IND_CMD.NUM_FACT_PK=DWH_COMMISSION.NUM_FACT_PK(+)  )
    Il faudra aussi m'expliquer cette jointure externe:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    AND  ( DWH_IND_CMD.NUM_FACT_PK=DWH_FACT.NUM_FACT_PK(+)  )

  6. #6
    Modérateur
    Avatar de Waldar
    Homme Profil pro
    Sr. Specialist Solutions Architect @Databricks
    Inscrit en
    Septembre 2008
    Messages
    8 453
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 46
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Sr. Specialist Solutions Architect @Databricks
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2008
    Messages : 8 453
    Points : 18 394
    Points
    18 394
    Par défaut
    Citation Envoyé par dragon74 Voir le message
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    AND  ( DWH_AGENT.CODE_AGENT=DWH_COMMISSION.NUM_AGENT_PK(+)  )
    AND  ( DWH_IND_CMD.NUM_CMD_PK=DWH_COMMISSION.NUM_CMD_PK (+)
    AND DWH_IND_CMD.NUM_LG_PK=DWH_COMMISSION.NUM_LG_PK(+)
    AND DWH_IND_CMD.NUM_FACT_PK=DWH_COMMISSION.NUM_FACT_PK(+)  )
    Attention, en jointure A-B-C, si on joint de façon externe A à B et B à C, le (+) doit suivre "l'extérieur" :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    AND DWH_COMMISSION.NUM_CMD_PK(+) = DWH_IND_CMD.NUM_CMD_PK
    AND DWH_AGENT.CODE_AGENT(+) = DWH_COMMISSION.NUM_AGENT_PK

  7. #7
    Membre confirmé Avatar de juvamine
    Profil pro
    Chef de projet MOA
    Inscrit en
    Mai 2004
    Messages
    414
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations professionnelles :
    Activité : Chef de projet MOA
    Secteur : Agroalimentaire - Agriculture

    Informations forums :
    Inscription : Mai 2004
    Messages : 414
    Points : 502
    Points
    502
    Par défaut
    C'est tout bon pour moi, pour la requête merci
    en effet je n'avais pas changer les "deux" (+)

    Merci à Waldar

    A + tard

    juva

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Jointure qui ne fonctionne pas
    Par kcizth dans le forum SQL
    Réponses: 4
    Dernier message: 26/02/2008, 18h36
  2. Plein de jointures qui ne fonctionnent pas
    Par petchos dans le forum Langage SQL
    Réponses: 4
    Dernier message: 03/08/2007, 14h53
  3. jointure qui ne fonctionne pas
    Par zulot dans le forum Langage SQL
    Réponses: 3
    Dernier message: 14/06/2006, 15h53
  4. [SQL] Requête à jointure qui ne fonctionne pas
    Par Bensor dans le forum Langage SQL
    Réponses: 2
    Dernier message: 09/12/2004, 17h10
  5. Jointure externe qui ne fonctionne pas
    Par Guizz dans le forum Langage SQL
    Réponses: 3
    Dernier message: 05/02/2004, 13h26

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo