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 :

Threads => help !


Sujet :

C

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre confirmé
    Inscrit en
    Février 2008
    Messages
    67
    Détails du profil
    Informations forums :
    Inscription : Février 2008
    Messages : 67
    Par défaut Threads => help !
    Hello,

    Je voudrais optimiser mon programme. Dans ce programme j'ai une fonction dont voici le prototype : char genere(int nombre);

    Cette fonction fait appele elle même à d'autre fonction assez lente, du coup, je me suis renseigné et j'ai vu que je pouvais utiliser les threads (sous windows). Si j'ai bien compris, ce sont des petits process qui utilisent la même mémoire que le process père, autrement dit, au lieu d'appeler une fois la fonction, je peux l'appeler plusieurs fois via les thread, et donc augmenter la vitesse d'execution de mon programme.

    Bref, dans le cas présent, j'utilise une fonction qui génénère des nombres, donc si j'ai bien compris, j'appele une fois ma fonction normalemen, et ensuite je la rappele via les threads, pour la lancer en parallèle.

    Ma question est simple : comment faire ?

    J'ai lu un tuto sur sur les thread, j'ai pigé la théorie, mais je suis allé voire des exemples sur d'autres sites, je n'ai rien trouvé qui aille dans le sens du tuto (tout était différent), à ne rien y comprendre.

    Donc voilà, j'aimerais qu'on me montre comment utiliser les threads, de façon simple, claire et avec des exemples.

    Merci !

  2. #2
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Au niveau système, sous Windows, deux solutions:
    • Utiliser les fonctions _beginthreadex() (pour lancer le thread), WaitForSingleObject() (pour attendre qu'il se termine) et CloseHandle() (pour libérer les ressources)
    • Télécharger la bibliothèque pthread-win32 qui permet d'utililiser les fonctions de multithread POSIX


    Au niveau du multithreading lui-même, il faut déjà que ton algorithme soit parallélisable. Le principe, c'est que les traitements ne doivent pas être exactement les mêmes sur les deux threads, ce qui serait inutile.
    Par exemple, si tu veux répartir sur plusieurs threads une fonction qui fait la somme des entiers d'un tableau, il faut que chaque thread traite une partie différente du tableau. Et ensuite, chacun retourne sa somme partielle, et le thread principal fait l'addition.


    Exemple pour la somme sur deux threads:
    • Algorithme: somme entrelacée (chaque thread compte de deux en deux).
    • Remplir une structure de paramètres pour le second thread : Adresse du tableau, taille du tableau, index de départ (ici, 1) + une place pour retourner la somme partielle.
    • Créer le nouveau thread avec cette structure.
    • Faire la même chose dans le thread principal, mais en partant de 0 au lieu de 1
    • Une fois la boucle finie, attendre que l'autre thread se termine.
    • Additionner les sommes partielles.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  3. #3
    Membre confirmé
    Inscrit en
    Février 2008
    Messages
    67
    Détails du profil
    Informations forums :
    Inscription : Février 2008
    Messages : 67
    Par défaut
    Merci pour cette réponse, donc si j'ai bien compris, 2 threads ne doivent pas faire la même chose, soit le bout de code suivant (j'aime bien les exemples concrets ;p) :

    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
    #include <stdlib.h>
    #include <stdio.h>
    #include <conio.h>
    #include <time.h>
     
    #define NOMBRE 200
     
    char genereip(int nombreip);
     
    int main(int argc, char* argv[])
    {
    genereip(NOMBRE);
    system("PAUSE");    
    return 0;
    }
     
    char genereip(int nombreip)
    {
         int i; 
         for (i = 0 ; i < nombreip ; i++)
               {
               int max = 254;
               int min = 1;
               srand (time(NULL));
               int nb;
               nb=min+(int) (rand() % (max+1-min));
               char ip[12];
               sprintf(ip,"192.168.1.%d",nb4);
               char out[] = " > null";
               char commande [512];
     
               strcpy(commande, "ping -n 1 "); 
               strcat(commande, ip);
               strcat(commande, out);
     
               int ret = system (commande);
               if (ret==0)
                          { 
                          printf("ip : %s => online !\n", ip);
                          }
                          else
                          { 
                          printf("ip : %s => offline \n", ip);
                          }
     
               }
    }
    Mon code m'affiche une liste de 200 adresse ip aléatoirement sur un réseau locale. C'est très lent, j'utilise system("ping"), j'aimerais bien trouver une façn plus rapide de tester si l'ip répond ou non.. faute de mieux dans l'immédiat, je me tourne donc vers les thread.

    Donc si je suis le raisonnement plus haut, il faudrait par exemple que divise NOMBRE, par le nombre de thread que je veux pour qu'ensuite chacun génèrent et testent un nombre X d'ip.

    Pouvez-vous me montrer comme ça se présenterait sur ce code ? Un visuel m'aiderait énormément pour comprendre le fonctionnement de tout ça.

    Par ailleurs, j'ai entendu plusieurs choses concernant les threads, visiblement il y en a plusieurs sortent, il en ressort qu'il vaut mieux passer par les pthread, peut être plus chaud à comprendre, mais le code ne change pas de linux à windows. Pourriez vous m'en dire plus ?

  4. #4
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Tu suis le raisonnement comme il faut, mais je n'ai pas vraiment le temps aujourd'hui de te montrer comment faire...

    Par contre: Tu ne dois pas appeler srand() dans la boucle. Il ne faut l'appeler qu'une seule fois (à vue de nez, je dirais une fois par thread)
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  5. #5
    Membre confirmé
    Inscrit en
    Février 2008
    Messages
    67
    Détails du profil
    Informations forums :
    Inscription : Février 2008
    Messages : 67
    Par défaut
    Bon, j'ai troucé ceci :

    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
    #include <stdio.h>
     
    #include <pthread.h>
     
    static void *task_a (void *p_data)
    {
       int i;
     
       for (i = 0; i < 5; i++)
       {
          printf ("Hello world A (%d)\n", i);
       }
     
       (void) p_data;
       return NULL;
    }
     
    static void *task_b (void *p_data)
    {
       int i;
     
       for (i = 0; i < 7; i++)
       {
          printf ("Hello world B    (%d)\n", i);
       }
       (void) p_data;
       return NULL;
    }
     
    int main (void)
    {
       pthread_t ta;
       pthread_t tb;
     
       puts ("main init");
     
       pthread_create (&ta, NULL, task_a, NULL);
       pthread_create (&tb, NULL, task_b, NULL);
     
    #if 1
       pthread_join (ta, NULL);
       pthread_join (tb, NULL);
    #endif
     
       puts ("main end");
     
       return 0;
    }
    Puis-je partir sur cette base pour réaliser mon code ? Est-ce que cette utilisation des threads est adaptée à ce que je veux faire ?

  6. #6
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 393
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 393
    Par défaut
    Ce code utilise pthread, donc si tu es sous Windows tu vas devoir télécharger la bibliothèque pthread-win32.

    Ensuite, le code est pas mal, simplement il y a des chances que tu n'aies pas besoin de task_b.

    Et entre le pthread_create() et le pthread_join(), on mettra une moitié des calculs (l'autre étant dans task_a), comme dans mon exemple.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

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

Discussions similaires

  1. Tri multi-threadé
    Par Tifauv' dans le forum C
    Réponses: 8
    Dernier message: 28/06/2007, 09h00
  2. Réponses: 1
    Dernier message: 24/02/2007, 14h02
  3. Programmer des threads
    Par haypo dans le forum C
    Réponses: 6
    Dernier message: 02/07/2002, 13h53
  4. Réponses: 5
    Dernier message: 12/06/2002, 15h12
  5. [Kylix] Pb de Thread !!
    Par Anonymous dans le forum EDI
    Réponses: 1
    Dernier message: 25/04/2002, 13h53

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