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

Concurrence et multi-thread Java Discussion :

[Thread] traitement parallele avec executors


Sujet :

Concurrence et multi-thread Java

  1. #1
    Membre éprouvé

    Inscrit en
    Septembre 2004
    Messages
    108
    Détails du profil
    Informations forums :
    Inscription : Septembre 2004
    Messages : 108
    Par défaut [Thread] traitement parallele avec executors
    Voila, j'ai un grand tableau de double qu'on notera data,
    J'applique un traitement lourd sur chaque element du data

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
     
    double[] data;
    remplirData();
    for(int i=0 ; i<data.length; i++){
    double resultat = traitementlourd(data[i]);
    }
    Afin d'optimiser ce traitement qui dure quelques secondes (15s), j'ai pensé à utiliser le multi-threading, çad diviser le traitement sur plusieurs threads et chaque thread pas s'occuper d'une partie du tableau;

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    ouble[] data;
    remplirData();
    ExecutorService executor = Executors.newFixedThreadPool(2);
    int size = data.length;
    TraitementWorker worker1 = new TraitementWorker(0, size / 2);
    TraitementWorker worker2 = new TraitementWorker(size /2 +1 ,size - 1);
    executor.execute(worker1);
    executor.execute(worker2);
    executor.shutdown();
    Je croyais que ce code va parralléliser les traitements et j'obtiendrai un certain gain de perfs. Mais voilà, les deux threads s'executent chaqune en 15 secondes . Lorsque je lance un seul : 7s

    Est-ce que mon raisonnement est faux ou c'est qq chose d'autre ?

  2. #2
    Membre Expert
    Avatar de natha
    Profil pro
    Inscrit en
    Janvier 2006
    Messages
    2 346
    Détails du profil
    Informations personnelles :
    Localisation : Suisse

    Informations forums :
    Inscription : Janvier 2006
    Messages : 2 346
    Par défaut
    L'idéal serait que tu t'informes sur le fonctionnement du multi-threading en java. Pour ton traitement, sur un PC mono-proc, tu ne risques pas d'avoir un gain de perf car au lieu de faire 1x le même traitement, tu le fais 2 fois (ça augmente le nombre d'objet instanciés par exemple).

    Un autre exemple : j'avais une fois 4 gros objets à créer, chacun prenant dans les 4 secondes si je les faisais l'un à la suite. J'ai pensé au multi-thread et résultat : le premier prenais 5 secondes, le second 9s, le troisième 13s et le dernier 16s. Au total ça ne changeait rien (je rappelle que 4x4=16 ). Le truc c'est que le traitement du 4e objet est ralenti par le traitement en parallèle des 3 autres.

  3. #3
    Membre expérimenté
    Inscrit en
    Mai 2007
    Messages
    335
    Détails du profil
    Informations forums :
    Inscription : Mai 2007
    Messages : 335
    Par défaut
    - Vérifie que ton executor te lance bien les Worker dans 2 Thread séparés.
    (mettre un break point sur le Worker, les 2 Threads doivent s'arrêter)
    - Regarde si ton traitement n'utilise pas des objets synchronisés?

    - effectivement, c'est mieux d'avoir un dual core pour ça, c'est bien le cas?

  4. #4
    Membre éprouvé

    Inscrit en
    Septembre 2004
    Messages
    108
    Détails du profil
    Informations forums :
    Inscription : Septembre 2004
    Messages : 108
    Par défaut
    Merci pour vos réponses,

    non je n'ai pas de dual core et je vais pas tarder à faire un test dessus (théoriquement je dois observer un gain cette fois )

    je n'utilise pas des objets synchronisés, j'ai même divisé l'entrée des 2 threads en 2 tableaux séparés histoire d'être sûr.

    je vais me documenter encore plus sur le sujet et je vous informe si je trouve qq chose. (Il y a bien la bibliothèque javolution mais c'est un autre sujet)

    Si je résume bien, ma démarche n'est valide que sur des système multi-processeurs?

  5. #5
    Membre Expert
    Avatar de natha
    Profil pro
    Inscrit en
    Janvier 2006
    Messages
    2 346
    Détails du profil
    Informations personnelles :
    Localisation : Suisse

    Informations forums :
    Inscription : Janvier 2006
    Messages : 2 346
    Par défaut
    Citation Envoyé par komando Voir le message
    Si je résume bien, ma démarche n'est valide que sur des système multi-processeurs?
    Même pas forcément. Dans ton cas je vois pas l'utilité. Un multi-proc ne te donnera pas un gain significatif. Splitter un traitement long en 2 n'est pas efficace. Peut-être que ça serait plus efficace si tu le splittes en 10 par exemple.

  6. #6
    Membre expérimenté
    Inscrit en
    Mai 2007
    Messages
    335
    Détails du profil
    Informations forums :
    Inscription : Mai 2007
    Messages : 335
    Par défaut
    Citation Envoyé par komando Voir le message
    Si je résume bien, ma démarche n'est valide que sur des système multi-processeurs?
    Rien ne t'empêche de mettre au point tes Thread sur un mono-proc (il faut t'assurer que les Thread tourne bien en parallèle)
    par contre l'accélération ne sera possible qu'en multi-proc (tu a un risque de ralentir au contraire sur un monoproc)

    Citation Envoyé par natha Voir le message
    Même pas forcément. Dans ton cas je vois pas l'utilité. Un multi-proc ne te donnera pas un gain significatif. Splitter un traitement long en 2 n'est pas efficace. Peut-être que ça serait plus efficace si tu le splittes en 10 par exemple.
    Je ne suis pas sûr de comprendre pourquoi 10 Thread?
    Sur un plan théorique: 2 Thread de 15 secondes seront plus rapides qu'un seul de 30.
    Dans la pratique, il y a le risque que les Thread ne soient pas bien répartis entre processeurs, Augmenter leur nombre permet sans doute de palier à ce risque, mais c'est à verifier par expérimentation, et au cas par cas selon l'algo.

    Pour bien faire, il faudrait adapter le nombre de Thread au nombre de proc:4, 8 ou plus:sur les serveurs, ça peut arriver, et dans l'avenir, on aura plus couramment des quad-core.

  7. #7
    Membre Expert
    Avatar de natha
    Profil pro
    Inscrit en
    Janvier 2006
    Messages
    2 346
    Détails du profil
    Informations personnelles :
    Localisation : Suisse

    Informations forums :
    Inscription : Janvier 2006
    Messages : 2 346
    Par défaut
    Citation Envoyé par deltree Voir le message
    Je ne suis pas sûr de comprendre pourquoi 10 Thread?
    Sur un plan théorique: 2 Thread de 15 secondes seront plus rapides qu'un seul de 30.
    Ce que je veux dire c'est que dans son cas il splitte le traitement pour traiter 2 moitiés de données. Ce n'est pas forcément les threads ici qui feraient gagner du temps mais le fait qu'il splitte.
    Il sera peut-être plus efficace de créer 10 tableaux de 100 entrées que 1 tableau de 1000 entrées. Mais bon, difficile de dire ce qui est le mieux sans savoir ce qu'il a dans son "traitementLong".

  8. #8
    Membre habitué
    Inscrit en
    Juin 2007
    Messages
    14
    Détails du profil
    Informations forums :
    Inscription : Juin 2007
    Messages : 14
    Par défaut
    Je pense que même pour une architecture simple core et mono processeur, MultiThreader le calcul peut le rendre plus rapide...

    En effet le Processeur possede un pipeline qui lui permet de commencer une nouvelle instruction avant que la précédente soit terminée... Et de plus un calcul complexe va surement utiliser des zones différentes du processeur (unités de calculs différentes...) ...

    Bref avec un calcul mono Threadé le processeur ne sera peut être pas utilisé a 100% tout le temps... en le décomposant il y a plus de chance que cela arrive... car pendant qu'un Thread travaille sur une zone ... un autre pourra travailler sur une autre...

    Evidement cela reste moins performant qu'un vrai multiprocesseur mais le gain n'est pas négligeable...

    De mon coté j'effectue régulierement des calculs multithreadés en Java et j'ai presque toujours obtenu des amelioration en multithreadant...

    Par contre pour tes Executor dsl mais je ne vais pas pouvoir trop t'aider je ne connais pas cette classe... ^^

  9. #9
    Membre confirmé Avatar de cyrille37
    Profil pro
    Développeur informatique
    Inscrit en
    Juin 2005
    Messages
    155
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Juin 2005
    Messages : 155
    Par défaut Executors.newFixedThreadPool
    L'usage d'Executors est simple et super pratique.
    Voici un exemple de code. C'est un copier/coller alors il va manquer quelques variables mais tu as comme ça le patron d'usage.

    L'idée est des remplir un tableau de "Callables" et de le passer à l'Executor qui va utiliser sont pool de thread.

    Le bout de code permet de vérifier des signatures SDA en parallèle (j'ai des machines multiproc).
    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
     
    int thCount = 10;
    ExecutorService e = Executors.newFixedThreadPool( thCount );
    ArrayList<Callable<Boolean>> callables = new ArrayList<Callable<Boolean>>();
    for( int j = 0; (j < thCount*100) && (j < loopCount); j++ , callablesCount++ )
    {
     callables.add( new DSASignCheck( publicKey, sign, message) );
    }
    List<Future<Boolean>> results = e.invokeAll( callables );
    for( Future<Boolean> f : results )
    {
     if( f.get() == Boolean.FALSE )
     {
      System.out.println("La signature de match pas");
     }
    }

  10. #10
    Membre Expert
    Avatar de Patriarch24
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Septembre 2003
    Messages
    1 047
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Industrie

    Informations forums :
    Inscription : Septembre 2003
    Messages : 1 047
    Par défaut
    Peut-on avoir une idée de ce que fait ton fameux "traitement lourd" ?
    Pour optimiser, je commencerai par là. En effet, lancer plusieurs threads en parallèle peut faire gagner du temps, mais pas toujours : ils ne vont pas s'exécuter en même temps sur une machine mono proc, mais en entrelacé. Malgré l'utilisation de pipelines, le coût des changements de contextes sont au total plus lourds que ton traitement (c'est ce qui fait que le traitement est ralenti avec deux threads). A ta place, je commencerais par regarder si je ne peux pas optimiser les calculs, qui sur les doubles sont de toutes façons couteux. Si ça n'améliore rien, calibre le nombre de threads que tu vas utiliser (essaye avec 3, 4, ..., suivant la taille du tableau !). Pense à utiliser des profilers pour vérifier le gain que tu obtiens.

Discussions similaires

  1. taches paralleles avec thread
    Par nicogigo dans le forum Général Python
    Réponses: 4
    Dernier message: 26/03/2010, 10h39
  2. Réponses: 2
    Dernier message: 04/01/2007, 16h48
  3. Plusieurs boucles en parallele avec Timers
    Par micniv dans le forum Access
    Réponses: 4
    Dernier message: 06/12/2006, 16h55
  4. Traitement Particulier Avec Dbnavigate??
    Par songue77 dans le forum Bases de données
    Réponses: 4
    Dernier message: 13/07/2006, 10h41
  5. [Threads] Actions continues avec des threads
    Par MiJack dans le forum Concurrence et multi-thread
    Réponses: 6
    Dernier message: 10/10/2005, 17h32

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