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

Langage SQL Discussion :

Requête circulaire ?


Sujet :

Langage SQL

  1. #1
    Membre expert
    Avatar de s.n.a.f.u
    Homme Profil pro
    Développeur Web
    Inscrit en
    Août 2006
    Messages
    2 760
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 50
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Août 2006
    Messages : 2 760
    Points : 3 545
    Points
    3 545
    Par défaut Requête circulaire ?
    Bonjour,

    Je ne sais pas si le titre est exact, mais il me semble que cela existe.

    Tout d'abord, je vous donne une structure simplifié de la table que je souhaite attaquer :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    ID (clé primaire)
    CHAMP1 (clé étrangère)
    CHAMP2
    CHAMP2 est une zone numérique nullable.
    Il peut bien sûr exister plusieurs tuples (CHAMP1, CHAMP2)

    Et je voudrais sélectionner tous les CHAMP1 qui ne sont pas complètement renseignés. C'est à dire que CHAMP1 a des lignes avec CHAMP2 renseigné ET aussi des lignes avec CHAMP2 null.

    J'ai réussi avec des sous-requêtes à base de ID IN (SELECT ...), mais je crois me rappeller qu'il est possible d'effectuer une requête "circulaire", avec une jointure sur la même table pour obtenir ce résultat.
    A defaut, obtenir un résultat inverse, CHAMP1 avec uniquement des CHAMP2 nulls par exemple, pourrait convenir.

    N'est-ce pas possible ?

    Merci,

    JM

    PS : c'est un peu tordu comme explications, je pourrais essayer de clarifier les points qui ne vous conviennent pas.
    • Avant de poser une question, n'hésitez pas à chercher dans la FAQ et les forums
    • Merci d'utiliser les balises de code (# dans l'éditeur)
    • N'oubliez pas de vous servir des boutons , et

    S.N.A.F.U

  2. #2
    Membre expérimenté Avatar de scheu
    Inscrit en
    Juin 2007
    Messages
    1 506
    Détails du profil
    Informations forums :
    Inscription : Juin 2007
    Messages : 1 506
    Points : 1 734
    Points
    1 734
    Par défaut
    Si j'ai bien compris ton problème, tu peux essayer un truc du style (à tester)
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    SELECT A.champ1 
    FROM ta_table A 
    WHERE A.champ2 IS NOT NULL 
    AND EXISTS 
    (SELECT 1 
     FROM ta_table B 
     WHERE A.champ1=B.champ1 
     AND B.champ2 IS NULL
    La théorie, c'est quand on sait tout mais que rien ne fonctionne.
    La pratique, c'est quand tout fonctionne mais que personne ne sait pourquoi.
    Ici, nous avons réuni théorie et pratique : Rien ne fonctionne ... et personne ne sait pourquoi !

    Réplication de base avec Postgresql : http://scheu.developpez.com/tutoriel.../log-shipping/

  3. #3
    Membre expert
    Avatar de s.n.a.f.u
    Homme Profil pro
    Développeur Web
    Inscrit en
    Août 2006
    Messages
    2 760
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 50
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Août 2006
    Messages : 2 760
    Points : 3 545
    Points
    3 545
    Par défaut
    Citation Envoyé par scheu Voir le message
    Si j'ai bien compris ton problème, tu peux essayer un truc du style (à tester)
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    SELECT A.champ1 
    FROM ta_table A 
    WHERE A.champ2 IS NOT NULL 
    AND EXISTS 
    (SELECT 1 
     FROM ta_table B 
     WHERE A.champ1=B.champ1 
     AND B.champ2 IS NULL
    Bonjour,

    Tu as tout à fait compris, et c'est à peu près ce genre de requête que je soumet actuellement.
    Mais j'aimerais trouver, même si ce n'est que pour ma culture personnelle, un moyen de faire quelquechose qui commencerait comme ça :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    SELECT DISTINCT(A.CHAMP1) FROM maTable AS A INNER/OUTER/LEFT/MACHIN JOIN maTable AS B ON A.ID = B.ID ...
    Suis-je en plein délire hallucinatoire ?
    • Avant de poser une question, n'hésitez pas à chercher dans la FAQ et les forums
    • Merci d'utiliser les balises de code (# dans l'éditeur)
    • N'oubliez pas de vous servir des boutons , et

    S.N.A.F.U

  4. #4
    Membre averti

    Profil pro
    Inscrit en
    Juillet 2005
    Messages
    418
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2005
    Messages : 418
    Points : 328
    Points
    328
    Par défaut
    Bonjour.
    Rien n'empêche effectivement de faire des auto-jointure (une table avec elle-même). Ca se passe exactement comme n'importe qu'elle jointure, mais dans ton cas, je n'ai pas vraiment saisie les conditions de jointure... Par exemple :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    SELECT A.champ1 
    FROM ta_table A, ta_table B
    WHERE A.ID=B.ID 
    and A.champ1=B.champ1 
    and A.champ2 IS NOT NULL 
    AND B.champ2 IS NULL
    ou, si tu préfères :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    SELECT A.champ1 
    FROM ta_table A inner/outer join ta_table B 
    on A.ID=B.ID
    WHERE A.champ1=B.champ1 
    and A.champ2 IS NOT NULL 
    AND B.champ2 IS NULL
    et pourquoi pas :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    SELECT A.champ1 
    FROM ta_table A inner/outer join ta_table B 
    on A.ID=B.ID
    and A.champ1=B.champ1 
    WHERE A.champ2 IS NOT NULL 
    AND B.champ2 IS NULL
    Je dirais a priori que c'est mieux niveau performances que le EXISTS, mais je peux me tromper...

  5. #5
    Membre expert
    Avatar de s.n.a.f.u
    Homme Profil pro
    Développeur Web
    Inscrit en
    Août 2006
    Messages
    2 760
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 50
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Août 2006
    Messages : 2 760
    Points : 3 545
    Points
    3 545
    Par défaut
    Merci, c'était ça.

    Voici ce qui effectue ce que je souhaite :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    SELECT A.CHAMP1
    FROM maTable AS A INNER JOIN maTable AS B ON A.CHAMP1 = B.CHAMP1
    WHERE A.CHAMP2 IS NULL AND B.CHAMP2 IS NOT NULL
    GROUP BY A.CHAMP1
    C'est nickel, et ça me donne bien les CHAMP1 qui existent avec les deux valeurs (alimenté ou null). C'est pratique non ?

    Merci Marchand de Sable, le terme autojointure m'a sauté aux yeux !
    La mémoire ou l'alcool, faut choisir, mais un bon Islay en programmant, c'est quand même pas mal !
    • Avant de poser une question, n'hésitez pas à chercher dans la FAQ et les forums
    • Merci d'utiliser les balises de code (# dans l'éditeur)
    • N'oubliez pas de vous servir des boutons , et

    S.N.A.F.U

  6. #6
    Membre averti

    Profil pro
    Inscrit en
    Juillet 2005
    Messages
    418
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2005
    Messages : 418
    Points : 328
    Points
    328
    Par défaut
    lol

    De rien, je comprends très bien ce cas de conscience

    N'oublie pas le [Résolu]

  7. #7
    ced
    ced est déconnecté
    Rédacteur/Modérateur

    Avatar de ced
    Homme Profil pro
    Gestion de bases de données techniques
    Inscrit en
    Avril 2002
    Messages
    6 029
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Loiret (Centre)

    Informations professionnelles :
    Activité : Gestion de bases de données techniques
    Secteur : Agroalimentaire - Agriculture

    Informations forums :
    Inscription : Avril 2002
    Messages : 6 029
    Points : 23 751
    Points
    23 751
    Par défaut
    Citation Envoyé par marchand_de_sable Voir le message
    Je dirais a priori que c'est mieux niveau performances que le EXISTS, mais je peux me tromper...
    Oui, parce qu'il n'y a plus de sous-requête.
    Voici un lien vers un tutoriel qui explique tout ça : optimisation de requêtes

    ced
    Rédacteur / Modérateur SGBD et R
    Mes tutoriels et la FAQ MySQL

    ----------------------------------------------------
    Pensez aux balises code et au tag
    Une réponse vous a plu ? N'hésitez pas à y mettre un
    Je ne réponds pas aux questions techniques par message privé, les forums sont là pour ça

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

Discussions similaires

  1. [AC-2007] référence circulaire causé par requête
    Par le_sayan dans le forum Requêtes et SQL.
    Réponses: 4
    Dernier message: 09/07/2010, 16h42
  2. Utilisation de MAX dans une requête SQL
    Par Evil onE dans le forum Langage SQL
    Réponses: 7
    Dernier message: 15/06/2004, 18h38
  3. Requete requête sous sybase
    Par eddie dans le forum Sybase
    Réponses: 3
    Dernier message: 02/04/2003, 14h51
  4. Requête imbriquée et indexes INTERBASE
    Par vadim dans le forum InterBase
    Réponses: 2
    Dernier message: 06/09/2002, 16h15
  5. [BDD] Enregistrer le résultat d'une requête
    Par Mowgly dans le forum C++Builder
    Réponses: 5
    Dernier message: 19/06/2002, 15h26

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