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

Développement SQL Server Discussion :

optimisation d'une vue avec plusieurs sous-requêtes


Sujet :

Développement SQL Server

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre à l'essai
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2012
    Messages
    5
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Boutique - Magasin

    Informations forums :
    Inscription : Mars 2012
    Messages : 5
    Par défaut optimisation d'une vue avec plusieurs sous-requêtes
    Bonjour,

    je dois définir une vue sur des tables A et B
    La table B doit être utilisée plusieurs fois avec A avec des conditions différentes.
    J'utilise donc des sous-requêtes.
    Voici un extrait de mon code :
    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 SUM(B.heures) FROM B
        WHERE B.col1 IN ('2','3') AND B.col2='NE' AND A.ID=B.ID) 
        AS req_B_1,
    (SELECT SUM(B.montant) FROM B
        WHERE B.col1 IN ('2','3') AND B.col2='NE' AND AND A.ID=B.ID) 
        AS req_B_2,
    (SELECT SUM(B.heures) FROM B
        WHERE B.col1='5' AND STR_TYPE='NE' AND AND A.ID=B.ID) 
        AS req_B_3,
    (SELECT SUM(B.montant) FROM B
        WHERE SB.col1='5' AND STR_TYPE='NE' AND AND A.ID=B.ID) 
        AS req_B_4,
    ...
    Le problème est que j'ai environ 20 sous-requêtes comme celles ci-dessus, et que cela plombe le temps d'exécution. D'autant plus qu'on ne peut retourner qu'une seule valeur par requête: dans mon exemple, j'utilise 2 sous-requêtes avec les mêmes conditions pour récupérer le nombre d'heures et le montant . De plus B comporte plusieurs millions de lignes.
    Y-a-t-il une solution plus performante ? (utiliser une table CTE qui ne comporterait que les lignes A.ID=B.ID ?)

    Merci à l'avance de votre aide
    Jean

  2. #2
    Membre éprouvé
    Homme Profil pro
    Administrateur de base de données
    Inscrit en
    Juin 2011
    Messages
    118
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Administrateur de base de données
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2011
    Messages : 118
    Par défaut
    Bonjour,

    Pourrais tu nous fournir le DDL des 2 tables ?
    Et la totalité des colonnes que tu dois retourner ?

    Ces informations sont essentielles pour déterminer une solution optimisée, surtout pour l'utilisation des index.

  3. #3
    Membre éprouvé

    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    1 448
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Juillet 2006
    Messages : 1 448
    Par défaut
    Quelque chose du genre :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    SELECT
     SUM(CASE WHEN B.col1 IN ('2','3') AND B.col2='NE' THEN B.heures END) AS req_B_1
     , SUM(CASE WHEN B.col1 IN ('2','3') AND B.col2='NE' THEN B.montant END) AS req_B_2
     , ...
    FROM A
    INNER JOIN B ON (
     A.ID=B.ID
    )

  4. #4
    Membre à l'essai
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2012
    Messages
    5
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Boutique - Magasin

    Informations forums :
    Inscription : Mars 2012
    Messages : 5
    Par défaut
    Merci SergeJack,

    Mais l'utilisation de CASE...WHEN augmente le temps de réponse énormément.
    Concernant la table qui fait 5 millions d'enregistrements, elle ne comporte ni d clé primaire ni index !
    Je vais voir si j'ai l'autorisation d'en rajouter.

  5. #5
    Membre éprouvé

    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    1 448
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Juillet 2006
    Messages : 1 448
    Par défaut
    Citation Envoyé par jean62 Voir le message
    Merci SergeJack,

    Mais l'utilisation de CASE...WHEN augmente le temps de réponse énormément.
    Ha.
    Ce n'est pas logique, surtout en l'absence de clés.

    Est-ce que vous pourriez mettre au complet les deux query, celui que vous aviez à l'origine et celui que je suggérai.

    À mon avis vous avez oubliez des filtres dans le seconds et pourtant présents dans le premier (genre : WHERE A.ID = 5).

  6. #6
    Membre à l'essai
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2012
    Messages
    5
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Pas de Calais (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Boutique - Magasin

    Informations forums :
    Inscription : Mars 2012
    Messages : 5
    Par défaut
    Citation Envoyé par Sergejack Voir le message
    Ha.
    Ce n'est pas logique, surtout en l'absence de clés.

    Est-ce que vous pourriez mettre au complet les deux query, celui que vous aviez à l'origine et celui que je suggérai.

    À mon avis vous avez oubliez des filtres dans le seconds et pourtant présents dans le premier (genre : WHERE A.ID = 5).
    Voici mon code:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    SUM(CASE WHEN B.col1 IN ('2','3') AND B.col2='NE' THEN B.heures END) AS req_B_1,
    SUM(CASE WHEN B.col1 IN ('2','3') AND B.col2='NE' THEN B.montant END) AS  req_B_2,
    avec la jointure suivante:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    LEFT OUTER JOIN B
    ON  A_ID = B_ID
    Je ne pense pas m'etre trompé. Mais je vous rappelle que j'ai 17 SUM(CASE...)
    dans le code, et que je ramène par ailleurs plus de 50 colonnes provenant de 5 tables différentes. D'autre part, votre méthode oblige à l'agrégat GROUP BY sur tous les autres champs.
    Merci de votre patience.
    Jean

  7. #7
    Membre Expert
    Inscrit en
    Août 2009
    Messages
    1 073
    Détails du profil
    Informations forums :
    Inscription : Août 2009
    Messages : 1 073
    Par défaut
    Il vaut mieux faire les sommes avant la jointure (et ainsi s'éviter le group by l'ensemble des colonnes ramenées) :

    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
     
    WITH sumB AS
    (
    SELECT B_ID
              ,SUM(CASE WHEN B.col1 IN ('2','3') AND B.col2='NE' THEN B.heures END) AS req_B_1
              ,SUM(CASE WHEN B.col1 IN ('2','3') AND B.col2='NE' THEN B.montant END) AS  req_B_2
               ...
      FROM B
     WHERE ..
     GROUP BY B_ID
    )
    SELECT req_B_1
              ,req_B_2
              , ...
      FROM A
              LEFT OUTER JOIN sumB ON (sumB.B_ID= A.A_ID)

Discussions similaires

  1. Stratégie pour une application avec plusieurs vues "empilées"
    Par camus3 dans le forum Windows Presentation Foundation
    Réponses: 6
    Dernier message: 20/12/2010, 15h15
  2. Une seule table plusieurs sous-requêtes
    Par mbeernow dans le forum Requêtes
    Réponses: 5
    Dernier message: 16/09/2010, 09h51
  3. Réponses: 10
    Dernier message: 09/02/2010, 20h08
  4. ORACLE 9.2 : Création d'une vue avec plusieurs clauses WHERE
    Par soffinette dans le forum Administration
    Réponses: 4
    Dernier message: 01/02/2007, 10h51
  5. Créer une vue avec des requêtes UNION ?
    Par webtheque dans le forum MS SQL Server
    Réponses: 2
    Dernier message: 04/04/2005, 12h37

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