Operation de reduction sur un ensemble de variables distribuees

  
Principe

MPI_max

Maximum

MPI_Min

Minimum

MPI_Sum

Somme

MPI_Prod

Produit

MPI_Land

Et logique

MPI_Band

Et binaire

MPI_Lor

Ou logique

MPI_Bor

Ou binaire

MPI_Lxor

Ou exclusif logique

MPI_Bxor

Ou exclusif binaire

MPI_Maxloc

Maximum et rang du processus qui a ce maximum

MPI_Minloc

Minimum et rang du processus qui a ce maximum

Programme : 

#include "mpi.h"

#include <stdio.h>

#include <math.h>

/* on a besoin d'une structure pour recuperer a la fois le maxi ou le mini et le numero du processeur */

typedef struct st { double valeur ; int num_proc ; } cell ;

#define SIZE 1000

int main(argc,argv) int argc; char *argv[];

{

    double startwtime, endwtime;

    int namelen, numprocs, myid, size, i ;

    char processor_name[MPI_MAX_PROCESSOR_NAME], buff[SIZE], msg[SIZE] ;

    cell entree[10], sortie[10] ;

    MPI_Init(&argc,&argv); startwtime = MPI_Wtime();

    MPI_Comm_size(MPI_COMM_WORLD,&numprocs);

    MPI_Comm_rank(MPI_COMM_WORLD,&myid);

    MPI_Get_processor_name(processor_name,&namelen);

    fprintf(stderr,"\nProcessus %d sur la machine %s parmi %d processus.\n", myid, processor_name, numprocs);

    if (numprocs != 3) fprintf(stderr,"Il me faut 3 processus !\n") ;

    /* initialisation des valeurs du tableau sur chaque processus*/

    for (i=0; i<10; i++) { entree[i].valeur = sin((double)(i+1)*(myid+1)) ; entree[i].num_proc=myid ; }

    /* on cherche a lire une structure compose d'un double puis un entier */

    MPI_Reduce( entree, sortie, 10, MPI_DOUBLE_INT, MPI_MAXLOC, 0, MPI_COMM_WORLD );

    if (myid==0) /* processus qui collecte les resultats */

    {

      fprintf(stderr,"%d donne le resultat de la reduction du maximum.\n",myid) ;

      for (i=0; i<10; i++)

      {

        fprintf(stderr,"%deme maximum : %g est sur %d\n",i,sortie[i].valeur,sortie[i].num_proc ) ;

        sortie[i].valeur = -1.0 ; sortie[i].num_proc = -1 ;

      }

    }

    MPI_Reduce( entree, sortie, 10, MPI_DOUBLE_INT, MPI_MINLOC, 0, MPI_COMM_WORLD );

    if (myid==0)

    {

      fprintf(stderr,"%d donne le resultat de la reduction du minimum.\n",myid) ;

      for (i=0; i<10; i++)

        fprintf(stderr,"%deme minimum : %g est sur %d\n",i,sortie[i].valeur,sortie[i].num_proc);

    }

    system("sleep 3") ;

    /** heure de fin **/

    endwtime = MPI_Wtime();

    printf("Temps ecoule sur %d = %f\n", myid, endwtime-startwtime);

    /** fin du pg **/

    MPI_Finalize();

    return 0;

}

Resultat :

Processus 0 sur la machine lil. parmi 3 processus.

Processus 1 sur la machine lil. parmi 3 processus.

Processus 2 sur la machine lil. parmi 3 processus.

0 donne le resultat de la reduction du maximum.

0eme maximum : 0.909297 est sur 1

1eme maximum : 0.909297 est sur 0

2eme maximum : 0.412118 est sur 2

3eme maximum : 0.989358 est sur 1

4eme maximum : 0.650288 est sur 2

5eme maximum : -0.279415 est sur 0

6eme maximum : 0.990607 est sur 1

7eme maximum : 0.989358 est sur 0

8eme maximum : 0.956376 est sur 2

9eme maximum : 0.912945 est sur 1

0 donne le resultat de la reduction du minimum.

0eme minimum : 0.14112 est sur 2

1eme minimum : -0.756802 est sur 1

2eme minimum : -0.279415 est sur 1

3eme minimum : -0.756802 est sur 0

4eme minimum : -0.958924 est sur 0

5eme minimum : -0.750987 est sur 2

6eme minimum : 0.656987 est sur 0

7eme minimum : -0.905578 est sur 2

8eme minimum : -0.750987 est sur 1

9eme minimum : -0.988032 est sur 2

Temps ecoule sur 1 = 3.032664

Temps ecoule sur 2 = 3.023845

Temps ecoule sur 0 = 3.148574


Ph. RIS 1997