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 :

remplacer NOT IN par NOT EXISTS


Sujet :

SQL Oracle

  1. #1
    Nouveau membre du Club
    Inscrit en
    Septembre 2005
    Messages
    51
    Détails du profil
    Informations forums :
    Inscription : Septembre 2005
    Messages : 51
    Points : 38
    Points
    38
    Par défaut remplacer NOT IN par NOT EXISTS
    est-ce que remplacer le NOT IN par NOT EXISTS permet de gagner de la performance? merci d'écrire l'instruction avec NOT EXISTS et quel est le gain obtenu?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    select S.DAY_ID, o.Mag_ID, o.mag_desc
    from Vtes_ld  s 
         , Mag_dm   o
    where s.Mag_KEY = o.Mag_KEY
    and S.DAY_ID NOT IN (select T.DAY_ID from Day_dmT where T.YR_ID <= 2009)
    and o.Mag_ID = '9595'

  2. #2
    Modérateur
    Avatar de al1_24
    Homme Profil pro
    Retraité
    Inscrit en
    Mai 2002
    Messages
    9 080
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 63
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Retraité
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mai 2002
    Messages : 9 080
    Points : 30 805
    Points
    30 805
    Par défaut
    Le remplacement du NOT IN par un NOT EXISTS donne en principe une requête plus performante, qui tentera de s'exécuter comme une jointure et utiliser les index disponibles à cet effet.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    SELECT  s.day_id
        ,   o.mag_id
        ,   o.mag_desc
    FROM    vtes_ld s
        INNER JOIN
            mag_dm  o
            ON  s.mag_key = o.mag_key
    WHERE   o.mag_id  = '9595'
        AND NOT EXISTS 
            (   SELECT  1 
                FROM    day_dm  t 
                WHERE   t.yr_id <= 2009
                    AND s.day_id = t.day_id 
            )
    PS : Es-tu sur que mag_id est une chaîne ?
    Modérateur Langage SQL
    Règles du forum Langage SQL à lire par tous, N'hésitez pas à consulter les cours SQL
    N'oubliez pas le bouton et pensez aux balises
    [code]
    Si une réponse vous a aidé à résoudre votre problème, n'oubliez pas de voter pour elle en cliquant sur
    Aide-toi et le forum t'aidera : Un problème exposé sans mentionner les tentatives de résolution infructueuses peut laisser supposer que le posteur attend qu'on fasse son travail à sa place... et ne donne pas envie d'y répondre.

  3. #3
    En attente de confirmation mail
    Inscrit en
    Mars 2010
    Messages
    205
    Détails du profil
    Informations forums :
    Inscription : Mars 2010
    Messages : 205
    Points : 230
    Points
    230
    Par défaut
    NOT EXISTS n'est pas la panacée, le chemin d'accès que prendra Oracle dépend des statistiques présentes sur les objets concernés et des paramétrages de ta base. Par exemple, j'ai vu récemment une requête en NOT EXISTS dériver sur un plen de jointure NESTED LOOPS, alors que le NOT IN nous donnait un HASH JOIN beaucoup plus efficace. Le NOT IN est optimisé depuis la 8i au moins, et peut également donner des plans d'exécutions corrects.

  4. #4
    Expert éminent sénior
    Avatar de orafrance
    Profil pro
    Inscrit en
    Janvier 2004
    Messages
    15 967
    Détails du profil
    Informations personnelles :
    Âge : 46
    Localisation : France

    Informations forums :
    Inscription : Janvier 2004
    Messages : 15 967
    Points : 19 073
    Points
    19 073
    Par défaut
    Citation Envoyé par al1_24 Voir le message
    Le remplacement du NOT IN par un NOT EXISTS donne en principe une requête plus performante
    Pas forcément. Ca dépend surtout de la taille du sous-ensemble. Par ailleurs, NOT IN et NOT EXISTS n'ont pas le même comportement alors attention de bien vérifier que ça ne change pas les contraintes applicatives.

    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
    23
    24
    25
    26
    27
    28
    29
    30
    31
    SQL> create table tab_in(id number);
     
    Table created.
     
    SQL> insert into tab_in values (1);
     
    1 row created.
     
    SQL> insert into tab_in values (2);
     
    1 row created.
     
    SQL> insert into tab_in values (3);
     
    1 row created.
     
    SQL> create table tab_notin(id number);
     
    Table created.
     
    SQL> insert into tab_notin values (1);
     
    1 row created.
     
    SQL> insert into tab_notin values (2);
     
    1 row created.
     
    SQL> insert into tab_notin values (null);
     
    1 row created.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    SQL> select * from tab_in where id not in (select id from tab_notin);
     
    no rows selected
     
    SQL> select * from tab_in t1 where not exists (select 1 from tab_notin t2
      2  where t1.id=t2.id);
     
            ID
    ----------
             3
     
    SQL>

  5. #5
    Modérateur
    Avatar de Waldar
    Homme Profil pro
    Customer Success Manager @Vertica
    Inscrit en
    Septembre 2008
    Messages
    8 452
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 46
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Customer Success Manager @Vertica
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2008
    Messages : 8 452
    Points : 17 820
    Points
    17 820
    Par défaut
    En plus de la réponse d'orafrance, j'ajouterai que les comportements entre NOT IN et NOT EXISTS se rejoignent de plus en plus avec les versions d'Oracle.

    En 11g ça donne quasiment toujours le même plan d'exécution, en gardant à l'esprit la différence de comportement sur présence d'un null.

    De mon côté, j'utilise NOT IN quand j'ai une petite liste d'id à filtrer, NOT EXISTS quand je traite des plus grosses volumétries. Mais ce n'est pas une règle empirique.

  6. #6
    Membre averti Avatar de mongilotti
    Profil pro
    Inscrit en
    Février 2003
    Messages
    314
    Détails du profil
    Informations personnelles :
    Localisation : Tunisie

    Informations forums :
    Inscription : Février 2003
    Messages : 314
    Points : 303
    Points
    303
    Par défaut
    merci de marque ce sujet comme résolu.

Discussions similaires

  1. [MySQL] Requête sur table de jointure avec not in ou not exists
    Par GueloSuperStar dans le forum Langage SQL
    Réponses: 12
    Dernier message: 08/03/2013, 15h01
  2. NOT IN et NOT EXISTS
    Par rsc dans le forum SQL
    Réponses: 10
    Dernier message: 20/09/2012, 08h06
  3. NOT IN et NOT EXISTS TRES long
    Par jdonet dans le forum Langage SQL
    Réponses: 5
    Dernier message: 23/09/2009, 18h10
  4. Remplacer une cellule par une zone de texte dans un script existant
    Par beegees dans le forum Général JavaScript
    Réponses: 4
    Dernier message: 26/10/2008, 16h57
  5. [9i] Not in ou not exists
    Par billout9 dans le forum SQL
    Réponses: 9
    Dernier message: 30/10/2007, 09h36

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