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 :

Optimisation de requête avec deux jointures [12c]


Sujet :

SQL Oracle

  1. #1
    Membre averti Avatar de rockley
    Homme Profil pro
    Inscrit en
    Décembre 2010
    Messages
    404
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Décembre 2010
    Messages : 404
    Points : 346
    Points
    346
    Par défaut Optimisation de requête avec deux jointures
    Bonjour à tous,

    J'ai la requête ci-dessous
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    select count(1) from  table_1 a 
    inner join table_2 b on a.ID = b.table_1_ID
    inner join table_3 c on a.ID = c.table_1_ID
    where ... ;
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
     
    ----------------------------------------------------------------------------------------------
    | Id  | Operation            | Name                  | Rows  | Bytes | Cost (%CPU)| Time     |
    ----------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT     |                       |     1 |    24 |    29   (0)| 00:00:01 |
    |   1 |  SORT AGGREGATE      |                       |     1 |    24 |            |          |
    |*  2 |   FILTER             |                       |       |       |            |          |
    |*  3 |    HASH JOIN OUTER   |                       |   206 |  4944 |    29   (0)| 00:00:01 |
    |*  4 |     TABLE ACCESS FULL| table_2               |   534 |  5340 |     4   (0)| 00:00:01 |
    |   5 |     TABLE ACCESS FULL| table_3               |  1157 | 16198 |    25   (0)| 00:00:01 |
    ----------------------------------------------------------------------------------------------
    Je voulais l'optimiser pour ne plus faire de Table Access full. J'ai donc changé la requête comme ci-dessous pour utiliser les index :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    select /*+ INDEX(b table_2_IX) INDEX(c table_3_IX) */ count(1) from  table_1 a 
    inner join table_2 b on a.ID = b.table_1_ID
    inner join table_3 c on a.ID = c.table_1_ID
    where ... ;
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    -------------------------------------------------------------------------------------------------------------------
    | Id  | Operation                             | Name                      | Rows  | Bytes | Cost (%CPU)| Time     |
    -------------------------------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT                      |                           |     1 |    24 |  1387   (0)| 00:00:01 |
    |   1 |  SORT AGGREGATE                       |                           |     1 |    24 |            |          |
    |*  2 |   HASH JOIN                           |                           |   206 |  4944 |  1387   (0)| 00:00:01 |
    |*  3 |    TABLE ACCESS BY INDEX ROWID BATCHED| table_2                   |   534 |  5340 |   541   (0)| 00:00:01 |
    |   4 |     INDEX FULL SCAN                   | table_2_IX                |  1079 |       |     4   (0)| 00:00:01 |
    |   5 |    TABLE ACCESS BY INDEX ROWID BATCHED| table_3                   |  1157 | 16198 |   846   (0)| 00:00:01 |
    |*  6 |     INDEX FULL SCAN                   | table_3_IX                |  1157 |       |     5   (0)| 00:00:01 |
    -------------------------------------------------------------------------------------------------------------------
    Je me retrouve donc a faire un INDEX FULL SCAN ce qui est beaucoup plus long que la lecture complète des tables.

    Auriez-vous des idées pour m'aider à optimiser cette requête ? Me dire ce que vous en pensez et si vous trouvez ça normal.
    Merci d'avance pour votre aide.

    Cordialement,

  2. #2
    Membre chevronné
    Homme Profil pro
    Développeur Oracle
    Inscrit en
    Décembre 2019
    Messages
    1 138
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Développeur Oracle

    Informations forums :
    Inscription : Décembre 2019
    Messages : 1 138
    Points : 1 918
    Points
    1 918
    Par défaut
    Bonjour,

    L'utilisation d'un hint pour forcer l'utilisation d'un index est quasiment toujours une mauvaise idée. Si un full table scan est utilisé c'est que le CBO l'a préféré à l'utilisation des index.-D'après le plan d'exécution la volumétrie est plutôt faible. Pourquoi as-tu besoin d'optimiser la requête? En quoi pose-t-elle problème?
    De plus il nous faudrait la requête complète, avec la clause WHERE, car c'est elle qui peut faciliter l'utilisation d'un index.

    Est-ce que les stats sont bien à jour sur toutes les table impliquées?
    Quelle sont les structures des tables (pk, fk et index)?

  3. #3
    Membre averti Avatar de rockley
    Homme Profil pro
    Inscrit en
    Décembre 2010
    Messages
    404
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Décembre 2010
    Messages : 404
    Points : 346
    Points
    346
    Par défaut
    Bonjour vanagreg,

    Merci pour ta réponse.
    Effectivement je pense que le CBO n’utilise pas les index car les tables n’ont pas beaucoup d’enregistrements.
    Je n'ai pas encore l'habitude de travailler sur les DB Oracle.
    Je trouvais étrange qu'en passant par les index on mette plus de temps. Mais plus je lis les forum plus je me dis que c'est normal.

    Cordialement,

  4. #4
    Membre expérimenté

    Homme Profil pro
    Inscrit en
    Mars 2010
    Messages
    536
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Mars 2010
    Messages : 536
    Points : 1 359
    Points
    1 359
    Par défaut
    Bonjour,


    Citation Envoyé par rockley Voir le message
    Bonjour à tous,

    Je voulais l'optimiser pour ne plus faire de Table Access full. J'ai donc changé la requête comme ci-dessous pour utiliser les index :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    select /*+ INDEX(b table_2_IX) INDEX(c table_3_IX) */ count(1) from  table_1 a 
    inner join table_2 b on a.ID = b.table_1_ID
    inner join table_3 c on a.ID = c.table_1_ID
    where ... ;
    Il ne peut y avoir un accès indexé (index range/unique scan) sur la deuxième table ("probe table") dans une jointure du type HASH JOIN en utilisant uniquement le colonne de jointure fournie pas la "hash table". C'est le fonctionnement propre de l'algorithme HASH JOIN. Lorsque vous avez forcé l'utilisation de l'index Oracle a opté pour un INDEX FULL SCAN qui veut dire lire l'entièreté de l'index du début à la fin et dans l'ORDRE.

    Il y a une exception à cette règle lorsque vous ajoutez, par exemple, un prédicat sur la colonne de jointure en la comparant à une valeur constante

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
     WHERE
           t1.id1 = t2.id
       AND t2.id = 10 -- ici
      ;
    Dans ce cas Oracle peut utiliser un INDEX RANGE/UNIQUE sur la deuxième table de la HASH JOIN

    Bien Cordialement
    Mohamed
    Bien Respectueusement
    www.hourim.wordpress.com

    "Ce qui se conçoit bien s'énonce clairement"

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

Discussions similaires

  1. Optimisation de requête avec jointure
    Par kineton dans le forum Requêtes
    Réponses: 8
    Dernier message: 27/08/2013, 13h47
  2. Optimisation de requête avec jointures
    Par ok.Idriss dans le forum Langage SQL
    Réponses: 4
    Dernier message: 08/12/2010, 20h44
  3. une requête avec deux jointures
    Par rinuom99 dans le forum Langage SQL
    Réponses: 6
    Dernier message: 18/12/2009, 20h11
  4. Optimisation de requête avec jointure textuelle
    Par spirou33 dans le forum Requêtes et SQL.
    Réponses: 10
    Dernier message: 26/10/2007, 09h36
  5. Optimisation de requête avec Tkprof
    Par stingrayjo dans le forum Oracle
    Réponses: 3
    Dernier message: 04/07/2005, 09h50

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