//Matrice vettore II strategia (per colonne)
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <mpi.h>
/**
* Funzione che esegue il prodotto matrice vettore
*/
void prod_mat_vett(double w[], double *a, int ROWS, int COLS, double v[])
{
int i, j;
for(i=0;i<ROWS;i++)
{
w[i]=0;
for(j=0;j<COLS;j++)
{
w[i] += a[i*COLS+j]* v[j];
}
}
}
int main(int argc, char **argv) {
int nproc; // Numero di processi totale
int me; // Il mio id
int m,n; // Dimensione della matrice
int local_n; // Dimensione dei dati locali
int i,j; // Iteratori vari
double T_inizio,T_fine,T_max;
// Variabili di lavoro
double *A, *At, *v, *local_v, *localA, *localAt, *local_w, *w;
//Attiva MPI/
MPI_Init(&argc, &argv);
//Trova il numero totale dei processi/
MPI_Comm_size (MPI_COMM_WORLD, &nproc);
//Da ad ogni processo il proprio numero identificativo/
MPI_Comm_rank (MPI_COMM_WORLD, &me);
// Se sono a radice
if(me == 0)
{
printf("inserire numero di righe m = \n");
printf("inserire numero di colonne n = \n"); // Numero di righe da processare
local_n = n/nproc;
// Alloco spazio di memoria
A
= malloc(m
* n
* sizeof(double));
//printf("v = \n");
for (j=0;j<n;j++)
{
v[j]=j;
// printf("%f ", v[j]);
}
// printf("\n");
// printf("A = \n");
for (i=0;i<m;i++)
{
for(j=0;j<n;j++)
{
if (j==0)
A[i*n+j]= 1.0/(i+1)-1;
else
A
[i
*n
+j
]= 1.0/(i
+1)-pow(1.0/2.0,j
); // printf("%f ", A[i*n+j] );
}
// printf("\n");
}
//Scrivo la matrice trasposta su cui eseguire le operazioni
At
=malloc(m
* n
* sizeof(double));for(i=0;i<n;i++)
{
for(j=0;j<m;j++)
{
At[i*m+j]=A[j*n+i];
}
}
} // fine me==0
// Spedisco m, n, local_n e v
MPI_Bcast(&m,1,MPI_INT,0,MPI_COMM_WORLD);
MPI_Bcast(&n,1,MPI_INT,0,MPI_COMM_WORLD);
MPI_Bcast(&local_n,1,MPI_INT,0,MPI_COMM_WORLD);
// 0 invia a tutti un pezzo del vettore v
if(me != 0)
local_v
=malloc(sizeof(double)*local_n
);MPI_Scatter(&v[0],local_n, MPI_DOUBLE, &local_v[0], local_n ,MPI_DOUBLE,0,MPI_COMM_WORLD);
// tutti allocano A locale e il vettore dei risultati
localA
= malloc(m
* local_n
* sizeof(double));localAt
= malloc(m
* local_n
* sizeof(double));local_w
= malloc(m
* sizeof(double));
// Adesso 0 invia a tutti un pezzo della matrice
int num = local_n*m;
MPI_Scatter(
&At[0], num, MPI_DOUBLE,
&localAt[0], num, MPI_DOUBLE,
0, MPI_COMM_WORLD);
// Scriviamo la matrice locale ricevuta
//printf("localA %d = \n", me);
for(i = 0; i < m; i++)
{
for(j = 0; j < local_n; j++)
{
localA[i*m+j]=localAt[j*(local_n+1)+i];
// printf("%lf\t", localA[i*m+j]);
}
// printf("\n");
}
// Effettuiamo i calcoli
T_inizio=MPI_Wtime();//inizio del cronometro per il calcolo del tempo di inizio
prod_mat_vett(local_w,localA,m,local_n,local_v);
T_fine=MPI_Wtime()-T_inizio; // calcolo del tempo di fine
// Eseguiamo le somme dei risultati ottenuti in ogni processore
MPI_Reduce(&local_w[0],&w[0],m,MPI_DOUBLE,MPI_SUM,0,MPI_COMM_WORLD);
MPI_Reduce(&T_fine,&T_max,1,MPI_DOUBLE,MPI_MAX,0,MPI_COMM_WORLD);
// 0 stampa la soluzione
if(me==0)
{
//printf("w = \n");
//for(i = 0; i < m; i++)
{
// printf("%f ", w[i]);
// printf("\n");
}
printf("\nTempo calcolo locale: %lf\n", T_fine
); printf("\nMPI_Reduce max time: %f\n",T_max
); }
MPI_Finalize (); /* Disattiva MPI */
return 0;
}
Ly9NYXRyaWNlIHZldHRvcmUgSUkgc3RyYXRlZ2lhIChwZXIgY29sb25uZSkKCiNpbmNsdWRlIDxzdGRpby5oPgojaW5jbHVkZSA8c3RkbGliLmg+CiNpbmNsdWRlIDxtYXRoLmg+CiNpbmNsdWRlIDxtcGkuaD4gCgoKLyoqCiogRnVuemlvbmUgY2hlIGVzZWd1ZSBpbCBwcm9kb3R0byBtYXRyaWNlIHZldHRvcmUKKi8Kdm9pZCBwcm9kX21hdF92ZXR0KGRvdWJsZSB3W10sIGRvdWJsZSAqYSwgaW50IFJPV1MsIGludCBDT0xTLCBkb3VibGUgdltdKQp7CiAgICBpbnQgaSwgajsKICAgIAogICAgZm9yKGk9MDtpPFJPV1M7aSsrKQogICAgewogICAgICAgIHdbaV09MDsKICAgICAgICBmb3Ioaj0wO2o8Q09MUztqKyspCiAgICAgICAgeyAKICAgICAgICAgICAgd1tpXSArPSBhW2kqQ09MUytqXSogdltqXTsKICAgICAgICB9IAogICAgfSAgICAKfQoKCmludCBtYWluKGludCBhcmdjLCBjaGFyICoqYXJndikgewoKaW50IG5wcm9jOyAgICAgICAgICAgICAgLy8gTnVtZXJvIGRpIHByb2Nlc3NpIHRvdGFsZQppbnQgbWU7ICAgICAgICAgICAgICAgICAvLyBJbCBtaW8gaWQKaW50IG0sbjsgICAgICAgICAgICAgICAgICAvLyBEaW1lbnNpb25lIGRlbGxhIG1hdHJpY2UKaW50IGxvY2FsX247ICAgICAgICAgICAgLy8gRGltZW5zaW9uZSBkZWkgZGF0aSBsb2NhbGkKaW50IGksajsgICAgICAgICAgICAgICAgICAgIC8vIEl0ZXJhdG9yaSB2YXJpIApkb3VibGUgVF9pbml6aW8sVF9maW5lLFRfbWF4OwovLyBWYXJpYWJpbGkgZGkgbGF2b3JvCmRvdWJsZSAqQSwgKkF0LCAqdiwgKmxvY2FsX3YsICpsb2NhbEEsICpsb2NhbEF0LCAqbG9jYWxfdywgKnc7CgoKLy9BdHRpdmEgTVBJLwpNUElfSW5pdCgmYXJnYywgJmFyZ3YpOwovL1Ryb3ZhIGlsIG51bWVybyB0b3RhbGUgZGVpIHByb2Nlc3NpLwpNUElfQ29tbV9zaXplIChNUElfQ09NTV9XT1JMRCwgJm5wcm9jKTsKLy9EYSBhZCBvZ25pIHByb2Nlc3NvIGlsIHByb3ByaW8gbnVtZXJvIGlkZW50aWZpY2F0aXZvLwpNUElfQ29tbV9yYW5rIChNUElfQ09NTV9XT1JMRCwgJm1lKTsKCi8vIFNlIHNvbm8gYSByYWRpY2UKaWYobWUgPT0gMCkKewogICAgcHJpbnRmKCJpbnNlcmlyZSBudW1lcm8gZGkgcmlnaGUgbSA9IFxuIik7IAogICAgZmZsdXNoKHN0ZG91dCk7CiAgICBzY2FuZigiJWQiLCZtKTsgCiAgICAKICAgIHByaW50ZigiaW5zZXJpcmUgbnVtZXJvIGRpIGNvbG9ubmUgbiA9IFxuIik7CiAgICBmZmx1c2goc3Rkb3V0KTsgCiAgICBzY2FuZigiJWQiLCZuKTsKICAgIC8vIE51bWVybyBkaSByaWdoZSBkYSBwcm9jZXNzYXJlCiAgICBsb2NhbF9uID0gbi9ucHJvYzsgIAogICAgCiAgICAvLyBBbGxvY28gc3BhemlvIGRpIG1lbW9yaWEKICAgIEEgPSBtYWxsb2MobSAqIG4gKiBzaXplb2YoZG91YmxlKSk7CiAgICB2ID0gbWFsbG9jKHNpemVvZihkb3VibGUpKm4pOwogICAgdyA9ICBtYWxsb2Moc2l6ZW9mKGRvdWJsZSkqbSk7IAogICAgCgkvL3ByaW50ZigidiA9IFxuIik7ICAgICAKICAgIGZvciAoaj0wO2o8bjtqKyspCiAgICB7CiAgICAJdltqXT1qOyAKICAgIC8vCXByaW50ZigiJWYgIiwgdltqXSk7Cgl9CiAgIC8vIHByaW50ZigiXG4iKTsKICAgIAogICAvLyBwcmludGYoIkEgPSBcbiIpOyAKICAgIGZvciAoaT0wO2k8bTtpKyspCiAgICB7CiAgICAgICAgZm9yKGo9MDtqPG47aisrKQogICAgICAgIHsKICAgICAgICAgICAgaWYgKGo9PTApCiAgICAgICAgICAgIEFbaSpuK2pdPSAxLjAvKGkrMSktMTsKICAgICAgICAgICAgZWxzZQogICAgICAgICAgICAgICAgQVtpKm4ral09IDEuMC8oaSsxKS1wb3coMS4wLzIuMCxqKTsgCiAgICAgICAgICAgLy8gcHJpbnRmKCIlZiAiLCBBW2kqbitqXSApOwogICAgICAgIH0KICAgICAgIC8vIHByaW50ZigiXG4iKTsKICAgIH0KCi8vU2NyaXZvIGxhIG1hdHJpY2UgdHJhc3Bvc3RhIHN1IGN1aSBlc2VndWlyZSBsZSBvcGVyYXppb25pCkF0PW1hbGxvYyhtICogbiAqIHNpemVvZihkb3VibGUpKTsKZm9yKGk9MDtpPG47aSsrKQogICB7CiAgICBmb3Ioaj0wO2o8bTtqKyspCiAgICAgICAgewogICAgICAgICBBdFtpKm0ral09QVtqKm4raV07CiAgICAgICAgIH0KICAgIH0KICAgICAKfSAvLyBmaW5lIG1lPT0wCmZmbHVzaChzdGRvdXQpOwovLyBTcGVkaXNjbyBtLCBuLCBsb2NhbF9uIGUgdgpNUElfQmNhc3QoJm0sMSxNUElfSU5ULDAsTVBJX0NPTU1fV09STEQpOyAgCk1QSV9CY2FzdCgmbiwxLE1QSV9JTlQsMCxNUElfQ09NTV9XT1JMRCk7ICAgICAgICAgICAgCk1QSV9CY2FzdCgmbG9jYWxfbiwxLE1QSV9JTlQsMCxNUElfQ09NTV9XT1JMRCk7ICAgICAgICAgICAgCgovLyAwIGludmlhIGEgdHV0dGkgdW4gcGV6em8gZGVsIHZldHRvcmUgdgppZihtZSAhPSAwKSAgCmxvY2FsX3Y9bWFsbG9jKHNpemVvZihkb3VibGUpKmxvY2FsX24pOwpNUElfU2NhdHRlcigmdlswXSxsb2NhbF9uLCBNUElfRE9VQkxFLCAmbG9jYWxfdlswXSwgbG9jYWxfbiAsTVBJX0RPVUJMRSwwLE1QSV9DT01NX1dPUkxEKTsgICAgICAgICAgICAKCi8vIHR1dHRpIGFsbG9jYW5vIEEgbG9jYWxlIGUgaWwgdmV0dG9yZSBkZWkgcmlzdWx0YXRpCgpsb2NhbEEgPSBtYWxsb2MobSAqIGxvY2FsX24gKiBzaXplb2YoZG91YmxlKSk7CmxvY2FsQXQ9IG1hbGxvYyhtICogbG9jYWxfbiAqIHNpemVvZihkb3VibGUpKTsKbG9jYWxfdyA9IG1hbGxvYyhtICogc2l6ZW9mKGRvdWJsZSkpOwoKLy8gQWRlc3NvIDAgaW52aWEgYSB0dXR0aSB1biBwZXp6byBkZWxsYSBtYXRyaWNlCmludCBudW0gPSBsb2NhbF9uKm07Ck1QSV9TY2F0dGVyKAogICAgJkF0WzBdLCBudW0sIE1QSV9ET1VCTEUsCiAgICAmbG9jYWxBdFswXSwgbnVtLCBNUElfRE9VQkxFLAogICAgMCwgTVBJX0NPTU1fV09STEQpOwoKLy8gU2NyaXZpYW1vIGxhIG1hdHJpY2UgbG9jYWxlIHJpY2V2dXRhCi8vcHJpbnRmKCJsb2NhbEEgJWQgPSBcbiIsIG1lKTsgCmZvcihpID0gMDsgaSA8IG07IGkrKykKewogICAgZm9yKGogPSAwOyBqIDwgbG9jYWxfbjsgaisrKQogICAgICAgewogICAgICAgIAogICAgICAgIGxvY2FsQVtpKm0ral09bG9jYWxBdFtqKihsb2NhbF9uKzEpK2ldOwogICAgICAgLy8gcHJpbnRmKCIlbGZcdCIsIGxvY2FsQVtpKm0ral0pOwogICAgICAgIH0KICAgLy8gcHJpbnRmKCJcbiIpOwp9CgovLyBFZmZldHR1aWFtbyBpIGNhbGNvbGkKVF9pbml6aW89TVBJX1d0aW1lKCk7Ly9pbml6aW8gZGVsIGNyb25vbWV0cm8gcGVyIGlsIGNhbGNvbG8gZGVsIHRlbXBvIGRpIGluaXppbwpwcm9kX21hdF92ZXR0KGxvY2FsX3csbG9jYWxBLG0sbG9jYWxfbixsb2NhbF92KTsKVF9maW5lPU1QSV9XdGltZSgpLVRfaW5pemlvOyAvLyBjYWxjb2xvIGRlbCB0ZW1wbyBkaSBmaW5lCi8vIEVzZWd1aWFtbyBsZSBzb21tZSBkZWkgcmlzdWx0YXRpIG90dGVudXRpIGluIG9nbmkgcHJvY2Vzc29yZQpNUElfUmVkdWNlKCZsb2NhbF93WzBdLCZ3WzBdLG0sTVBJX0RPVUJMRSxNUElfU1VNLDAsTVBJX0NPTU1fV09STEQpOwpNUElfUmVkdWNlKCZUX2ZpbmUsJlRfbWF4LDEsTVBJX0RPVUJMRSxNUElfTUFYLDAsTVBJX0NPTU1fV09STEQpOyAgICAgIAovLyAwIHN0YW1wYSBsYSBzb2x1emlvbmUKaWYobWU9PTApCnsgCiAgICAvL3ByaW50ZigidyA9IFxuIik7IAogICAgLy9mb3IoaSA9IDA7IGkgPCBtOyBpKyspCiAgICAgICB7CiAgICAgICAvLyBwcmludGYoIiVmICIsIHdbaV0pOwogICAgICAgLy8gcHJpbnRmKCJcbiIpOwogICAgICAgIH0KICAgcHJpbnRmKCJcblRlbXBvIGNhbGNvbG8gbG9jYWxlOiAlbGZcbiIsIFRfZmluZSk7CglwcmludGYoIlxuTVBJX1JlZHVjZSBtYXggdGltZTogJWZcbiIsVF9tYXgpOwp9CgpNUElfRmluYWxpemUgKCk7IC8qIERpc2F0dGl2YSBNUEkgKi8KcmV0dXJuIDA7ICAKfQ==