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

Requêtes MySQL Discussion :

Requête SQL (complexe ?)


Sujet :

Requêtes MySQL

  1. #1
    Membre à l'essai
    Homme Profil pro
    Développeur Web
    Inscrit en
    Décembre 2014
    Messages
    10
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haut Rhin (Alsace)

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Décembre 2014
    Messages : 10
    Points : 14
    Points
    14
    Par défaut Requête SQL (complexe ?)
    Bonjour,

    Je m'en remet à vous pour demander de l'aide. En effet, je n'arrive pas à construire ma requête SQL...

    Explication:

    J'ai une table dans laquelle il y a pas mal de données. Voici sa structure :

    id | ref | date | quantite | rupture

    Voici un exemple:
    Nom : 2015-10-06_133659.png
Affichages : 112
Taille : 10,0 Ko

    On peut donc voir qu'il y a pour une ref, plusieurs entrées avec des dates différentes ! (et ce, pour des milliers de ref)

    Ce que je souhaite: Récupérer l'entrée de chaque ref comportant la date la plus récente.

    Je vous remercie d'avance pour votre aide,
    AL

  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 786
    Points
    30 786
    Par défaut
    As-tu cherché un peu dans ce forum pour voir si ce type de question n'avait pas déjà été posée ?
    Tu devrais pouvoir y trouver quelques dizaines de réponses.
    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
    Membre à l'essai
    Homme Profil pro
    Développeur Web
    Inscrit en
    Décembre 2014
    Messages
    10
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haut Rhin (Alsace)

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Décembre 2014
    Messages : 10
    Points : 14
    Points
    14
    Par défaut
    J'avoue que je n'ai pas cherché longtemps al1_24. Mais ce pas par fainéantise, mais parce que je ne sais pas comment nommer ce que je cherche.

    J'ai bien trouvé cela :
    http://www.developpez.net/forums/d12...-plus-recente/

    Mais je n'arrive pas à l'appliquer dans mon cas et de plus je ne sais pas si c'est bien cela qu'il faut faire.

    EDIT : Je viens de trouver un post où vous avez répondu : http://www.developpez.net/forums/d97...derniere-date/

    J'ai donc essayé ceci :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    SELECT `ref`,`quantite`,`date` FROM `stock` s1 WHERE EXISTS (SELECT 1 FROM `stock` s2 WHERE s2.`ref` = s1.`ref` HAVING MAX(s2.`date`) = s1.`date`)
    La page à l'air de planter pour le moment, j'ai edit le message pour que vous sachiez que j'essaye une de vos astuces.

    EDIT2: Effectivement, la page directement dans phpmyadmin tourne dans le vide depuis quelques minutes

  4. #4
    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 786
    Points
    30 786
    Par défaut
    La table contient de très nombreuses lignes ?
    Est-elle indexée ? Un index sur (ref,date) serait un réel plus.

    Il y a d'autres réponses à ce problème. Celle-ci n'est peut être pas optimale pour MySQL.

    Ces autres réponses sont d'ailleurs proposées dans les discussions que tu as trouvées.
    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.

  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
    Essayez avec une jointure directe :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    select s1.ref, s1.quantite, s1.date
      from stock s1
      join ( select ref, max(date) as dt_max
               from stock
           group by ref) s2
        on s2.ref    = s1.ref
       and s2.dt_max = s1.date;

  6. #6
    Expert éminent sénior Avatar de Artemus24
    Homme Profil pro
    Agent secret au service du président Ulysses S. Grant !
    Inscrit en
    Février 2011
    Messages
    6 378
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Agent secret au service du président Ulysses S. Grant !
    Secteur : Finance

    Informations forums :
    Inscription : Février 2011
    Messages : 6 378
    Points : 19 054
    Points
    19 054
    Par défaut
    Salut oasisss.

    Citation Envoyé par oasisss
    Ce que je souhaite: Récupérer l'entrée de chaque ref comportant la date la plus récente.
    Ce sujet a déjà été traité, il y a très peu de temps dans ce forum.
    La solution instinctive consiste à rechercher la date ayant la date maximale pour une référence donnée.
    Voici ce que je propose :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    select id
    from {ta table] as tb1
    where date = (
        select max(date)
        from {ta table} as tb2
        where tb2.ref = tb1.ref
    );
    Suite à une discutions sur cette approche, il existe une autre façon de faire, plus rapide, qui permet de retrouver ce que tu cherches.
    A savoir, pour un ref donné, la ligne contenant la date la plus récente.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    select id
    from             {ta table} as tb1
    left outer join {ta table} as tb2
    on   tb2.ref = tb1.ref
    and tb2.date > tb1.date
    where tb2.ref is null;
    @+
    Si vous êtes de mon aide, vous pouvez cliquer sur .
    Mon site : http://www.jcz.fr

  7. #7
    Modérateur
    Avatar de escartefigue
    Homme Profil pro
    bourreau
    Inscrit en
    Mars 2010
    Messages
    10 130
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loir et Cher (Centre)

    Informations professionnelles :
    Activité : bourreau
    Secteur : Finance

    Informations forums :
    Inscription : Mars 2010
    Messages : 10 130
    Points : 38 543
    Points
    38 543
    Billets dans le blog
    9
    Par défaut
    Citation Envoyé par Artemus24 Voir le message
    Suite à une discutions sur cette approche, il existe une autre façon de faire, plus rapide, qui permet de retrouver ce que tu cherches.
    A savoir, pour un ref donné, la ligne contenant la date la plus récente.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    select id
    from             {ta table} as tb1
    left outer join {ta table} as tb2
    on   tb2.ref = tb1.ref
    and tb2.date > tb1.date
    where tb2.ref is null;
    Remarque intéressante, avez vous pu la tester en grandeur réelle, car de mon coté, sur une table de quelques milliers de lignes avec un index sur Ref1 (non unique, mais discriminant) et un index multiple sur la date, un explain me donne une meilleure stratégie d'accès pour la requête avec sub-select, mais dans les faits, l'écart n'est pas mesurable avec des volumes si faibles.

  8. #8
    Expert éminent sénior Avatar de Artemus24
    Homme Profil pro
    Agent secret au service du président Ulysses S. Grant !
    Inscrit en
    Février 2011
    Messages
    6 378
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Agent secret au service du président Ulysses S. Grant !
    Secteur : Finance

    Informations forums :
    Inscription : Février 2011
    Messages : 6 378
    Points : 19 054
    Points
    19 054
    Par défaut
    Salut Escartefigue.

    Je ne suis pas à l'origine de cette remarque, mais StringBuilder. Dans un autre sujet, sur le même problème, j'avais donné la première solution.
    StringBuilder m'a fait la remarque que l'on ne doit pas utiliser de sous-requête car elles ne sont pas très performantes.

    Quand je faisais du DB2 dans les version de 5 à 7, personne ne m'avait fait ce genre de remarque.
    Et j'ai toujours eu de bons résultats en terme de performance.

    Afin de vérifier les propos tenus par StringBuilder, j'ai fait des tests de performances sous MySql, et j'ai constaté qu'il avait raison.
    Maintenant, la véritable question est de savoir comment est traité la sous-requête selon le SGBDR que l'on utilise.

    Sur mon ordinateur et sur quelques milliers de lignes, j'ai un rapport environ de 1 pour la seconde solution contre 2 pour la première solution (la durée du temps d'exécution).
    Autrement dit, pour les deux approches, on se trouve dans un ordre de grande inférieur à 1/10 secondes.
    C'est peu être normal car je suis tout seul à travailler sur mon ordinaueur.

    Même si la seconde solution est plus performante que la première sous MySql, les deux solutions restent acceptables.
    Je n'ai pas testé sur des millions ou des milliards de lignes, mais je pense que le rapport doit s'agrandir, toujours en faveur de la seconde solutions.

    Le problème que nous avions tous les deux, c'est que nous avions des points de vue complètement opposés sur cette question.
    Il se trouve que j'ai pu remettre en cause l'opinion qu'avait StringBuilder sur la sous-requête.
    Et qu'inversement, sous MySql, je n'adopte plus la première solution.
    Mais à chaque fois que le thème revient dans ce forum, j'indique les deux solutions, en mettant l'accent sur la performance de la seconde solution.

    En conclusion, on ne peut pas généraliser sur ce qu'il faut préconiser avant d'avoir fait des tests sur le SGBDR que l'on utilise.
    Selon la volumétrie, selon aussi le nombre de lignes moyen à traiter pour une référence donnée, on peut avoir des résultats totalement différents.
    Mais dire qu'une sous-requête (je tiens à préciser, une sous-requête corrélée) est à exclure, ne doit pas être une idée préconçue avant de l'avoir testé.
    J'ai d'ailleurs remarqué que cette idée à tendance à se propager sur le net, comme une parole d'évangile.
    Dans les tests de performances, la seule réponse possible est "ça dépend du contexte !" et de ce fait, il ne fait jamais exclure quoi que ce soit avant de l'avoir testé.

    @+
    Si vous êtes de mon aide, vous pouvez cliquer sur .
    Mon site : http://www.jcz.fr

  9. #9
    Membre à l'essai
    Homme Profil pro
    Développeur Web
    Inscrit en
    Décembre 2014
    Messages
    10
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haut Rhin (Alsace)

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Décembre 2014
    Messages : 10
    Points : 14
    Points
    14
    Par défaut
    Je vous remercie tous pour votre aide.

    @al1_24 => En effet la table contient quelques 600 000 lignes (augmente tous les jours). Je n'avais pas mis d'index sur ces colonnes, ce que j'ai fais maintenant, merci.

    @Waldar => J'ai essayé votre requête et celle-ci fonctionne à merveille, merci beaucoup !

    @Artemus24 => En effet, je sais bien que ce sujet à déjà été traité, mais je n'arrivais pas à l'appliquer dans mon cas. Merci de tes réponses.


    Pour résumer, pour ceux qui tombent sur cette discussion en recherchant une solution au problème, la requête de Waldar fonctionne !

    Encore merci à tous ceux qui ont répondu (malgré que ce problème a déjà été traité)

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

Discussions similaires

  1. requête sql complexe
    Par julien_d dans le forum SQL
    Réponses: 7
    Dernier message: 01/05/2007, 17h03
  2. Requète SQL complexe
    Par NicoNGRI dans le forum MS SQL Server
    Réponses: 7
    Dernier message: 01/08/2006, 10h10
  3. Requête sql complexe
    Par new_wave dans le forum Langage SQL
    Réponses: 1
    Dernier message: 03/01/2006, 11h55
  4. Requête SQL Complexe
    Par zut94 dans le forum MS SQL Server
    Réponses: 1
    Dernier message: 25/11/2005, 20h53
  5. Requête SQL complexe. Comment faire ....
    Par BilTCD dans le forum Langage SQL
    Réponses: 4
    Dernier message: 05/11/2004, 16h18

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