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

Threads & Processus C++ Discussion :

Fonctionnement tres etrange de openMP


Sujet :

Threads & Processus C++

  1. #1
    Membre éprouvé Avatar de uriotcea
    Homme Profil pro
    Ingénieur / physicien
    Inscrit en
    Septembre 2003
    Messages
    1 301
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur / physicien
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2003
    Messages : 1 301
    Par défaut Fonctionnement tres etrange de openMP
    Bonjour,

    J'observe quelquechose de tres etrange avec openMP
    - Je calcul de temp necessaire pour une boucle de calcul
    - Ensuite je fais exactement la même chose mais avec une directive openMP du style "#pragma omp parallele for" pour 2 processeurs
    - j'en déduis que en dessous de 1000 iterations (n), paralléliser cette boucle n'est plus pertinant.
    example : (t1:sans threading, t2:avec 2 cores)

    n=100000 t1=10s , t2 =5s
    n=10000 t1=1s, t2=0.8s
    n=1000 t1=0.1s, t2=0.1s
    n=100 t1=0.01s t2=0.03s


    - J'ajoute une condition "if(n<1000)" dans ma directive et là commence les problemes. Si n est inferieur à 1000, le calcul n'est effectivement plus parallélisé (j'ai verifié) , mais les temps de calcul correspondent aux t2 et non au t1 comme je m'attendais. J'ai l'impression que le temps de gestion de la directive est toujours le même, "if" ou pas "if". Mais alors à quoi bon cette directive "IF". Ou ai-je oublié quelquechose ?

    Merci de vos suggestions

  2. #2
    Expert éminent
    Avatar de koala01
    Homme Profil pro
    aucun
    Inscrit en
    Octobre 2004
    Messages
    11 635
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 53
    Localisation : Belgique

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Octobre 2004
    Messages : 11 635
    Par défaut
    Salut,

    Le problème, c'est que, visiblement, n n'est connu qu'à l'exécution, alors que le pragma va agir... dés la compilation...

    Il faut, en effet, se rappeler que les directives préprocesseur (#include, #ifdef / #ifndef, #pragma,...) sont prises en compte avant même que la première ligne de code assembleur ne soit créée... et donc, ne peuvent agir que... sur les constantes connues à la compilation...

    Je vois donc deux solutions possibles, dont, il faut bien l'avouer, aucune n'est vraiment idéale:

    1. Soit, tu définis le nombre d'itération à la compilation (en passant -DITERATION=nombrediteration (syntaxe Gcc) ), mais cela t'obligera à compiler ton application chaque fois que le nombre d'itérations changera,
    2. Soit, tu crées deux applications distinctes:
      1. une application non parallèle à utiliser lorsque iteration < 1000
      2. une application utilisant le paralélisme à utiliser quand iteration > 1000
      mais tu auras alors le problème que l'utilisateur doit être considéré comme un imbécile distrait, et qu'il faut t'attendre à ce qu'il y en ait au moins un qui tente un jour d'utiliser une version alors qu'il devrait utiliser l'autre...
    Tu vois, que, comme je l'ai dit plus haut, aucune des solutions n'est vraiment idéale...

    Mais elles sont données "à chaud" et sans avoir réfléchi beaucoup plus que cela au problème, et il n'est pas impossible qu'il existe une troisième solution qui soit meilleure que ces deux ci
    A méditer: La solution la plus simple est toujours la moins compliquée
    Ce qui se conçoit bien s'énonce clairement, et les mots pour le dire vous viennent aisément. Nicolas Boileau
    Compiler Gcc sous windows avec MinGW
    Coder efficacement en C++ : dans les bacs le 17 février 2014
    mon tout nouveau blog

  3. #3
    Membre éprouvé Avatar de uriotcea
    Homme Profil pro
    Ingénieur / physicien
    Inscrit en
    Septembre 2003
    Messages
    1 301
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur / physicien
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2003
    Messages : 1 301
    Par défaut
    Merci de ta reponse, mais je pense que tu fais erreur. Je ne sais pas comment la directive du "IF" est interpretée, mais c'est bien dynamique, parce que le nombre de threads associé à mon application depend bien de la valeur de n. Je le verifie bien avec la charge de mes processeurs, le nbr de threads de l'appli ou même la commande "omp_get_num_threads()"

  4. #4
    screetch
    Invité(e)
    Par défaut
    lorsque tu utilises openMP il y a toujours un surcout lié au découpage en tâches, dispatching des taches, etc
    et ce, meme si il n'y a qu'un seul thread de travail (bouh! )
    ce que tu peux faire, c'est dynamiquement faire un
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    if(n>1000)
    {
      #pragma omp parallel for
    }
    else
    {
      // code tout con qui ne va pas etre ralentit par openMP
    }

  5. #5
    Membre éprouvé Avatar de uriotcea
    Homme Profil pro
    Ingénieur / physicien
    Inscrit en
    Septembre 2003
    Messages
    1 301
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur / physicien
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2003
    Messages : 1 301
    Par défaut
    Je pensais qu'avec un if(0) il n'y avait aucun decoupage, et que le code etait executé séquenciellement.
    Maintenant ce que tu suggere et de dupliquer tout le code parallélisable.
    C'est un peu lourd non

  6. #6
    Expert éminent
    Avatar de koala01
    Homme Profil pro
    aucun
    Inscrit en
    Octobre 2004
    Messages
    11 635
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 53
    Localisation : Belgique

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Octobre 2004
    Messages : 11 635
    Par défaut
    Citation Envoyé par uriotcea Voir le message
    Je pensais qu'avec un if(0) il n'y avait aucun decoupage, et que le code etait executé séquenciellement.
    Maintenant ce que tu suggere et de dupliquer tout le code parallélisable.
    C'est un peu lourd non
    Au pire, déporte (en fait, le terme correct est tu "factorise") le vers une fonction inline:
    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
    inline void privateFunction(/* argument */)
    {
        /* le code à dupliquer */
    }
     
    void foo()
    {
        if(iteration >1000)
        {
             #pragma omp parallel for
             privateFunction(/* arguments éventuels */);
        }
        else
        {
             privateFunction(/* arguments éventuels */);
        }
    }
    Nota: inline n'oblige absolument pas le compilateur à inliner la fonction...

    Mais, au pire, si tu t'arranges pour que la fonction ne soit appelée qu'une fois (AKA: que la boucle soit dans cette fonction "privée" et non dans la fonction appelante), la perte due à l'appel de fonction sera minime
    A méditer: La solution la plus simple est toujours la moins compliquée
    Ce qui se conçoit bien s'énonce clairement, et les mots pour le dire vous viennent aisément. Nicolas Boileau
    Compiler Gcc sous windows avec MinGW
    Coder efficacement en C++ : dans les bacs le 17 février 2014
    mon tout nouveau blog

  7. #7
    Membre éprouvé Avatar de uriotcea
    Homme Profil pro
    Ingénieur / physicien
    Inscrit en
    Septembre 2003
    Messages
    1 301
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur / physicien
    Secteur : Service public

    Informations forums :
    Inscription : Septembre 2003
    Messages : 1 301
    Par défaut
    La directive "#pragma omp parallel for" ne peut précéder qu'une instruction "for" !

Discussions similaires

  1. Bug ? peut-être, Etrange? très certainement
    Par Inarius dans le forum C#
    Réponses: 0
    Dernier message: 09/04/2010, 23h26
  2. Licenciement tres etrange
    Par berlioz_95870 dans le forum Licenciement
    Réponses: 4
    Dernier message: 02/10/2008, 14h07
  3. Réponses: 3
    Dernier message: 06/11/2007, 11h18
  4. [2.0][C#] cast tres etrange d'un control
    Par igorzup dans le forum ASP.NET
    Réponses: 11
    Dernier message: 28/12/2006, 12h08
  5. Probleme tres etrange avec une requete...
    Par Jim_Nastiq dans le forum Langage
    Réponses: 15
    Dernier message: 18/04/2006, 15h03

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