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

C# Discussion :

Enorme lenteur application


Sujet :

C#

  1. #1
    Candidat au Club
    Profil pro
    Inscrit en
    Octobre 2010
    Messages
    3
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2010
    Messages : 3
    Par défaut Enorme lenteur application
    Bonjour,
    J’ai quelques soucis de (grosse) lenteur avec une application que j’ai faite pour dédoublonner une base de données Access.
    (Je dois comparer que l’Id client est différent mais avec le même CP, le même code Insee, la même enseigne, la position X et la même position Y).
    Entant débutant je ne connais rien à l’objet, j’ai codé un programme qui récupère les données de mon select dans un Grid View que je n’affiche pas.
    Je parcours tous le Grid View en comparant les champs si c’est un doublon je mets l’id client dans un tableau
    puis j’envoie se tableau d’id client pour vérifier que celui-ci ne possède pas de campagne avant de le supprimer.
    Si l’id client ne possède pas de campagne je le mets dans un nouveau tableau pour effectuer la suppression de celui-ci plus tard.
    (Cette opération prend environ 8h)
    Puis je relance La même opération mais en commençant par la fin du Grid View pour vérifier qu’il ne reste pas de doublon sans campagne. (Cette opération prend environ 8h).
    Voici 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
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
     
    // rempli le DataSet et le GridView
    this.GridView_F5P.DataSource = this.Ds_carto.France5_p_copie;
    this.Ds_carto.Clear();
    this.FR_copie_carto.Fill(this.Ds_carto.France5_p_copie);
     
    for (i = 0; i < GridView_F5P.Rows.Count; i++)
    {
    // Si l'Id de la premiere n'est pas Tag comme traité (' different de 1')
    if (Convert.ToInt32(GridView_F5P.Rows[i].Tag) != 1)
          {
              for (j = 0; j < GridView_F5P.Rows.Count; j++)
              {
                // on compare que l'ID est different mais avec les memes : 
                // position X, position Y, C.P, code Insee, enseigne
    if ((Convert.ToInt32(GridView_F5P.Rows[i].Cells[0].Value) != Convert.ToInt32(GridView_F5P.Rows[j].Cells[0].Value)) && 
    (Convert.ToInt32(GridView_F5P.Rows[i].Cells[1].Value) == Convert.ToInt32(GridView_F5P.Rows[j].Cells[1].Value)) && 
    (GridView_F5P.Rows[i].Cells[2].Value.ToString() == GridView_F5P.Rows[j].Cells[2].Value.ToString()) && (GridView_F5P.Rows[i].Cells[3].Value.ToString() == GridView_F5P.Rows[j].Cells[3].Value.ToString()) && 
    (Convert.ToDouble(GridView_F5P.Rows[i].Cells[4].Value) == Convert.ToDouble(GridView_F5P.Rows[j].Cells[4].Value)) &&
    (Convert.ToDouble(GridView_F5P.Rows[i].Cells[5].Value) == Convert.ToDouble(GridView_F5P.Rows[j].Cells[5].Value)))
                {
                  // C'est un doublon
                  nb++;
                  // enregistre son Id
    tab[ind] = Convert.ToInt32(GridView_F5P.Rows[j].Cells[0].Value);
                   ind++;
                   z = i; i = j;
                   // On Tag cette Id comme traité ('1') dans la premiere table pour ne pas la retraiter
                   GridView_F5P.Rows[i].Tag = 1;
                   i = z;
                  }
                }
            }
       }
     
    // on envoie tous les Id present dans le tableau des doublon ('tab')
    // Si l'Id ne possede pas de campagne ('count inferieur ou égal 0')
    // on l'enregistre dans le tableau des doublons sans campagne('tab_camp')
     
    int ind2 = 0;       // indice du tableau des doublons sans campagne
    int i = 0;          // indice du tableau des doublons
    int nb = 0;         // permet de connaitre le nombre de doublon sans campagne
    int count = 0;
    // parcourt tous le tableau tant que l’ID est pas à zéro
    while (Convert.ToInt32(tab[i]) != 0)
    {
       count = (int)Det_Camp_carto.FillBy_recherche(Convert.ToInt32(tab[i]));
     
       if (count <= 0)
       {
           tab_camp[ind2] = Convert.ToInt32(tab[i]);
           ind2++;
           nb++;
       }
       i++;
     }
     lbl_camp.Text = "" + nb + " sans campagne";
    On me demande de faire en sorte que cela prenne moins de temps mais je ne sais pas comment faire.
    Est-ce que je dois le faire en objet ? Si oui pouvez-vous m’aiguiller ?

  2. #2
    Membre extrêmement actif

    Homme Profil pro
    Ingénieur R&D
    Inscrit en
    Juin 2003
    Messages
    4 506
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur R&D
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2003
    Messages : 4 506
    Par défaut
    Quelques pistes

    Je pense déjà que tu ne devrais pas utiliser un gridview qui n'est pas forcément très optimisé et plutôt réservé pour l'affichage (tu ne l'affiches même pas). Cherche plutôt à utiliser des collections qui sont plutôt performant sur cela

    Tu peux aussi chercher une solution utilisant une multithreading et chercher à paralléliser certaines choses en découpant le travail à faire

    Essayer de voir s'il n'y a pas moyen parfois de faire un break et de sortir d'une boucle for de niveau 3 ou 2.


    Avant de faire le traitement sur la base de données essayez de générer des index pour booster les requêtes

    Optimiser la requête SQL

    Puis tu ne montres pas tout le code notamment certaines fonctions qui peut être cache d'autres défauts

    J'espère que tu affiches une estimation du temps restant (genre nombre de ligne / nombre de ligne existant traités temps écoulé hh:mm:ss) parce que s'il faut attendre à chaque fois 8 heures cela va être dur de savoir si les modifications apportent quelque chose

  3. #3
    Expert confirmé Avatar de Graffito
    Profil pro
    Inscrit en
    Janvier 2006
    Messages
    5 993
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2006
    Messages : 5 993
    Par défaut
    Chargeons d'abord toute la DataTable triée :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    string sConnString = 
      "provider=Microsoft.JET.OLEDB.4.0; data source = myDatabase.mdb";
    string sCmdString = 
      "SELECT * FROM MyTableName ORDER BY CP, INSEE, ENSEGNE, X, Y, CAMPAGNE DESC";
    OleDbDataAdapter MyDataAdapter = new OleDbDataAdapter(sCmdString, sConnString);
    OleDbCommandBuilder cb = new OleDbCommandBuilder(dataAdapter);
    DataSet MyDataSet=new DataSet() ;
    MyDataAdapter.Fill(MyDataSet,"MyTableName");
    Mytable = MyDataSet.Tables["MyTableName"];
    Il sufft ensuite de traiter en séquence MyTable.Rows[i] en vérifiant si c'est un doublon par rapport à MyTable.Rows[i-1].

  4. #4
    Membre extrêmement actif

    Homme Profil pro
    Ingénieur R&D
    Inscrit en
    Juin 2003
    Messages
    4 506
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur R&D
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2003
    Messages : 4 506
    Par défaut
    Si tu es en 3.5 tu peux après la requête de Grafitto plutôt que de boucler sur les enregistrements faire une requêtes linq qui te renvoi les distinct (il me semble que distinct prends en paramètre un prédicat ?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    var distinct = (from d in mytable.Rows.AsEnumerable()
                       select d).Distinct("quelque chose ici à creuse?");
    Et var devrait contenir des données sans doublon. Au niveau perf cela reste à contrôler.

  5. #5
    Membre extrêmement actif

    Homme Profil pro
    Ingénieur R&D
    Inscrit en
    Juin 2003
    Messages
    4 506
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur R&D
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2003
    Messages : 4 506
    Par défaut
    au fait c'est quoi la taille de la base de données ?

  6. #6
    Candidat au Club
    Profil pro
    Inscrit en
    Octobre 2010
    Messages
    3
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2010
    Messages : 3
    Par défaut
    Bonjour,

    Merci pour toutes ces pistes. Que je vais tester de suite

    Pou répondre aux questions :

    Puis tu ne montres pas tout le code notamment certaines fonctions qui peut être cache d'autres défauts
    La chose que je ne montre pas ces la fonction qui calcul le temps de traitement (différence entre le moment de l'execution et le moment de la fin).

    J'espère que tu affiches une estimation du temps restant (genre nombre de ligne / nombre de ligne existant traités temps écoulé hh:mm:ss)
    parce que s'il faut attendre à chaque fois 8 heures cela va être dur de savoir si les modifications apportent quelque chose
    Non je n'affiche rien d'autre mais j'effectue mes essais sur un fichier de test qui possedent environ 1500 enregistrements et cela prend environ 1 min pour le traiter.
    Le programme passe 2400600 fois dans la 2ème boucle "For".

    au fait c'est quoi la taille de la base de données ?
    Ma bbd contient 90000 enregistrement donc en gros le programme fait 90000*90000 pour tous les comparer.

  7. #7
    Membre chevronné Avatar de MetalGeek
    Profil pro
    Inscrit en
    Octobre 2008
    Messages
    412
    Détails du profil
    Informations personnelles :
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations forums :
    Inscription : Octobre 2008
    Messages : 412
    Par défaut
    Salut,

    perso je ferais plutôt tout en SQL (regarde sur Developpez, y'a plein de tutos ; ce que tu veux faire n'est pas très chiadé).

  8. #8
    Expert confirmé Avatar de Graffito
    Profil pro
    Inscrit en
    Janvier 2006
    Messages
    5 993
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Janvier 2006
    Messages : 5 993
    Par défaut
    hegros : Et var devrait contenir des données sans doublon. Au niveau perf cela reste à contrôler.
    Mais, je crois qu'il veut au contraire récupérer le complément, c'est-à-dire les doublons, pour les éliminer.

  9. #9
    Membre extrêmement actif

    Homme Profil pro
    Ingénieur R&D
    Inscrit en
    Juin 2003
    Messages
    4 506
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur R&D
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2003
    Messages : 4 506
    Par défaut
    90000 enregistrements c'est pinuts. En effet c'est ton algorithme qui est à revoir il n'y a pas de raisons de passer 90000*90000 pour faire ce que tu veux. Et même avec cela 8H c'est énorme est-ce que ta machine utilise un processeur 8 bits ?

    Et effectivement en SQL cela devrait pouvoir s'écrire en une seule requête

    Graffito : autant pour moi.

  10. #10
    Expert éminent Avatar de Pol63
    Homme Profil pro
    .NET / SQL SERVER
    Inscrit en
    Avril 2007
    Messages
    14 204
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : .NET / SQL SERVER

    Informations forums :
    Inscription : Avril 2007
    Messages : 14 204
    Par défaut
    tu cherches juste quelques données dans ta base, donc ramener toute la table dans vb.net prend du temps, une fois ramené tu mets ca dans un datagridview ca prend à nouveau du temps, puis tu parcours chaque ligne du dgv, alors qu'à l'origine ta requete a déjà parcouru chaque ligne de la table pour te la ramener !
    et tout ca pour rien ! il suffit de ramener seulement les quelques lignes qui t'intéressent à savoir les quelques doublons, et laisser les données dans access, il cherchera bien plus vite que toi, surtout avec des indexes

    si j'ai bien compris tu cherches des clients ayant les meme CP, le même code Insee, la même enseigne, la position X et la même position Y, mais avec des Id différents

    la base pour trouver des doublons c'est ca :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    select cp, insee, enseigne, x, y from table group by cp, insee, enseigne, x, y having count(*) > 1
    cette requete va te donner cp, insee, enseigne, x, y qui se trouvent dans plus d'une ligne dans la table

    m'enfin on ne peut pas avoir les id avec une telle requete, il faut alors faire une ou deux autres requetes
    par exemple
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    select id, cp, insee, enseigne, x, y  from table inner join
    (select cp, insee, enseigne, x, y from table group by cp, insee,  enseigne, x, y having count(*) > 1) t on table.cp = t.cp and table.insee = t.insee and les autres aussi
    ce sont des syntaxes sql server, voir s'il y a des choses à changer pour access
    et puis il y a peut etre encore mieux

    multithreader sur access n'est pas forcément une bonne idée, surtout sur la meme table
    Cours complets, tutos et autres FAQ ici : C# - VB.NET

  11. #11
    Membre extrêmement actif

    Homme Profil pro
    Ingénieur R&D
    Inscrit en
    Juin 2003
    Messages
    4 506
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur R&D
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2003
    Messages : 4 506
    Par défaut
    Citation Envoyé par Pol63 Voir le message

    multithreader sur access n'est pas forcément une bonne idée, surtout sur la meme table
    Tu ne dois pas connaître rien chose en multithreading. Il ne s'agit pas de multithreadé des requêtes SQL mais de multithreadé des tâches qui peuvent l'être une fois les requêtes remontées.

    Typiquement tu peux découper le résultat d'une requête et en donner un morceau à différents threads (les 10000 premiers résultats au thread 1, les 10000 suivantes au thread 2 etc..)et donner rendez-vous à ces threads pour terminer le tout.

  12. #12
    Candidat au Club
    Profil pro
    Inscrit en
    Octobre 2010
    Messages
    3
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2010
    Messages : 3
    Par défaut
    Merci pour ta requête Pol63 cela m'a grandement aidé dans mon traitement maintenant cela prend environ 2 min au lieu de 8h cependant je suis quand même obligé de comparer les résultats 1 à 1 car la requête me sort le client original et tous ses doublons

  13. #13
    Membre éclairé
    Profil pro
    Inscrit en
    Mars 2004
    Messages
    54
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Mars 2004
    Messages : 54
    Par défaut SQL
    J'ai lu les précédents posts en diagonale et j'ai cru comprendre que tu dois comparer que l’Id client est différent mais avec le même CP, le même code Insee, la même enseigne, la position X et la même position Y

    Tu balances tout dans un Grid, puis tu travailles dessus ...
    En prime, tu n'affiches même pas ce Grid ...

    Le principe général est que le traitement des données d'une base de données doit se faire d'abord par le moteur de cette base de données

    Ton travail consiste donc à envoyer des requêtes SQL

    NB : Si base de données contient des doublons qu'il faut maintenant supprimer, c'est que la base de données a été mal définie au départ ... le responsable est donc le gestionnaire (et créateur) de cette base de données, ce serait donc à lui de réparer aujourd'hui la "merde" et non à un programmeur débutant. Une base de données qui est appelée à contenir des milliers d'enregistrements doit être définie de telle sorte que même si un programme fait n'importe quoi (tel qu'autoriser l'ajout de doublons), la base de données rejette les demandes faites par le programme. Une base de données n'est pas une poubelle ! ... où on peut stocker n'importe quoi

    Je ne suis pas français, mais si le code Insee est un identifiant unique, le plus simple ne serait-il pas de ne pas faire un programme, mais d'ouvrir Access et de faire le nécessaire ?

    NB : Un programme n'est pas quelque chose de magique qui peut tout faire, tout réparer. Un programme, c'est un outil. Et, on ne crée un programme que quand il n'existe pas d'outil pour faire ce qu'on veut faire. Ton outil, c'est Access. Inutile de créer un programme, tu ne feras pas mieux qu'Access. Il est quasi certain que les concepteurs d'Access ont déjà tout prévu en matière de gestion d'une base de données. Il suffit de savoir ce qu'Access a dans le ventre, au lieu de coder ce qui existe déjà de manière optimisée ...

    Sais-tu que dans Access, tu peux cliquer dans l'onglet "Requête", puis sur "Nouveau", puis choisir "Assistant Requête trouver les doublons" ...

    En trois clics, tu pourrais déjà avoir ta solution ...

    Je suis quasi certain que ton problème peut se résoudre sans taper une seule ligne de code, et qu'un bon administrateur de base de données peut réparer la base en moins d'une heure ! (si le problème ne porte que sur des doublons)

  14. #14
    Membre éclairé
    Profil pro
    Inscrit en
    Mars 2010
    Messages
    349
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2010
    Messages : 349
    Par défaut
    Hum pas faux lol mais peut-être avait-il d'autres besoins...

  15. #15
    Membre extrêmement actif

    Homme Profil pro
    Ingénieur R&D
    Inscrit en
    Juin 2003
    Messages
    4 506
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur R&D
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2003
    Messages : 4 506
    Par défaut
    Citation Envoyé par champomy62 Voir le message
    Hum pas faux lol mais peut-être avait-il d'autres besoins...
    Le besoin d'avoir des doublons ? Non rends toi à l'évidence un cochon est passé avant toi et c'est à toi de nettoyer la bouze. On est tous plus ou moins passé par là de toute façon

  16. #16
    Membre éclairé
    Profil pro
    Inscrit en
    Mars 2010
    Messages
    349
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2010
    Messages : 349
    Par défaut
    Oaui. Je suis totalement d'accord ! Mais bon au moins en regardant ce post j'ai appris des choses...

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

Discussions similaires

  1. [AC-2000] ENORMES lenteurs à l'ouverture d'un état
    Par r.louis dans le forum IHM
    Réponses: 3
    Dernier message: 27/01/2010, 17h24
  2. [WD14] Lenteur application et nombre fichiers ouverts
    Par Xsara 167 cv dans le forum WinDev
    Réponses: 3
    Dernier message: 09/03/2009, 13h17
  3. [WD 11] Lenteur Application
    Par arnaud_verlaine dans le forum WinDev
    Réponses: 1
    Dernier message: 06/02/2007, 22h25
  4. [PHP-JS] lenteur application php
    Par gregius dans le forum Langage
    Réponses: 10
    Dernier message: 13/10/2006, 16h43
  5. Lenteur application sous oracle 9i
    Par aketh dans le forum Autres Logiciels
    Réponses: 1
    Dernier message: 08/08/2006, 21h29

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