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 :

Tentative de reduction de temps de calcul avec openMP: ECHEC


Sujet :

Threads & Processus C++

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre averti
    Femme Profil pro
    Étudiant
    Inscrit en
    Novembre 2011
    Messages
    18
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant
    Secteur : Agroalimentaire - Agriculture

    Informations forums :
    Inscription : Novembre 2011
    Messages : 18
    Par défaut Tentative de reduction de temps de calcul avec openMP: ECHEC
    Bonjour a tous,
    J'aurais vraiment besoin de vos lumières

    J'ai un code assez long a exécuter, j'ai donc décidé de me pencher sur la parallélisation avec openMP

    J'ai reproduit un code jouet reprenant ce que je souhaiterais paralléliser dans mon vrai code: deux calculs de la même fonction (avec paramètres différents) sur deux cœurs en même temps.

    Voila 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
     
    #include <iostream>
    #include <iomanip>
    using namespace std;
    #include <boost/progress.hpp>
    #include<omp.h>
     
    double fct_test1(int r, int t) {
       double temp=0;
       temp = (2*r + 3*t + 200)/12;
       return temp;
    }
     
    double fct_test(int a , int b, int c, int r, int t) {
       double temp = 0;
       for (int i = 0; i < 2100000000; i++)
        {
        temp += ((a + 30*b + c*5)/(fct_test1(r,t)*100000000));
        }
       return temp;
    }
     
    int main() {
       boost::progress_timer time;
       double test = 0. ;
       double test_prop = 0. ;
     
       #pragma omp parallel
       {
        #pragma omp sections nowait
        {
           #pragma omp section
           {
             cout <<  omp_get_thread_num() << endl;
             test = fct_test(2,2,2,2,2) ;
           }
          #pragma omp section
          {
             cout << omp_get_thread_num() << endl;
             test_prop = fct_test(3,3,3,3,3) ;
          }
        }
    }
     
    cout << "test" << test << endl;
    cout << "test_prop" << test_prop << endl;
     
    return 0.;
     
    }
    Sans utiliser openMP mon code tourne en 4.22 secondes alors qu'en utilisant le code décrit ci-dessus il met 5.70 s !!!

    J'ai lu sur ce forum que l'appel des fonctions openMP est coutêux en temps, j'ai donc tenté ce type de code sur mon vrai programme (où la fonction demandée va mettre environ 20 secondes/ par réalisation) mais il se passe la même chose: les temps de calculs sont plus long...

    Peut-être n'ai-je pas bien utilisée la bibliothèque, peut être que c'est inutile de paralléliser ce type de code... je ne sais plus trop quoi faire

    Une idée ??

    Merci beaucoup,
    Nane

  2. #2
    Membre Expert Avatar de Ehonn
    Homme Profil pro
    Étudiant
    Inscrit en
    Février 2012
    Messages
    788
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Février 2012
    Messages : 788
    Par défaut
    Bonjour

    Sur le code que tu présentes, j'obtiens de bonnes performances avec OpenMP (un peu trop d'ailleurs).
    Je compile avec les options -O3 -march=native -fopenmp avec GCC 4.8.2.

  3. #3
    Membre averti
    Femme Profil pro
    Étudiant
    Inscrit en
    Novembre 2011
    Messages
    18
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant
    Secteur : Agroalimentaire - Agriculture

    Informations forums :
    Inscription : Novembre 2011
    Messages : 18
    Par défaut
    Bonjour Ehonn,
    Je viens de tester avec tes options (ajoutée aux miennes) avec une version gcc 4.4.6
    Extrait de mon makefile:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    CFLAGS= -O3 -march=native -fomit-frame-pointer -Wall -pipe -funroll-loops -fno-inline
    LDFLAGS = -fopenmp
    Mais rien n'y fait le temps d'exécution est toujours lent 5.75secondes...

    Penses-tu que ce soit la bonne écriture pour paralléliser ce genre de code?

    Merci

  4. #4
    Membre Expert Avatar de Ehonn
    Homme Profil pro
    Étudiant
    Inscrit en
    Février 2012
    Messages
    788
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Février 2012
    Messages : 788
    Par défaut
    Il faut mettre -fopenmp dans les CFLAGS aussi, sinon ton programme reste séquentiel.
    Au passage, -fomit-frame-pointer est déjà activé avec -O.
    Pour les options -funroll-loops -fno-inline, j'aurais tendance à laisser le compilateur choisir mais c'est toi qui choisis
    Avec GCC 4.8.2, j'ai eu des soucis avec -pipe en compilant qu'un seul fichier; j'ai pas cherché plus que ça (mauvaise utilisation, manque de place, ...) mais l'exécutable généré n'était pas correct :s
    (Sinon, tu as bien une machine avec plusieurs cœurs ?)

    Pour paralléliser le code j'aurais plutôt fait un truc du genre
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    #pragma omp parallel for reduction(+:temp)
    for (int i = 0; i < 2100000000; i++)
    {
        temp += ((a + 30*b + c*5)/(fct_test1(r,t)*100000000));
    }

  5. #5
    Membre averti
    Femme Profil pro
    Étudiant
    Inscrit en
    Novembre 2011
    Messages
    18
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant
    Secteur : Agroalimentaire - Agriculture

    Informations forums :
    Inscription : Novembre 2011
    Messages : 18
    Par défaut
    Je travail sur un calculateur qui a enormement de coeurs... (je ne sais plus le chiffre exact!)
    Je viens de re-tenter en modifiant le makefile : toujours les mêmes résultats.

    C'est vrai qu'en parallélisant la boucle directement, le gain de temps est réel mais ce code est un code jouet... et la fonction décrite ici
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    for (int i = 0; i < 2100000000; i++)
    {
        temp += ((a + 30*b + c*5)/(fct_test1(r,t)*100000000));
    }
    n'est pas la même que la réelle... (elle est beaucoup plus complexe en vrai!)

    Penses-tu qu'il y a un moyen de demander l’exécution de deux fonctions en même temps sur deux cœurs différents ?

  6. #6
    Membre Expert Avatar de Ehonn
    Homme Profil pro
    Étudiant
    Inscrit en
    Février 2012
    Messages
    788
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Février 2012
    Messages : 788
    Par défaut
    Et si tu lances ton exécutable (version OpenMP) comme ceci, tu obtiens quoi comme temps ?
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    export OMP_NUM_THREADS=1 && time ./ton_exe
    export OMP_NUM_THREADS=2 && time ./ton_exe
    export OMP_NUM_THREADS=4 && time ./ton_exe
    export OMP_NUM_THREADS=8 && time ./ton_exe

Discussions similaires

  1. Réponses: 5
    Dernier message: 06/06/2011, 01h04
  2. Mesure du temps de calcul avec time.clock()
    Par céline80 dans le forum Général Python
    Réponses: 2
    Dernier message: 21/09/2009, 17h02
  3. Réponses: 0
    Dernier message: 04/08/2008, 17h05
  4. Temps de calcul avec deux écrans
    Par Shaga dans le forum OpenGL
    Réponses: 2
    Dernier message: 14/11/2005, 09h24

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