Sie sind auf Seite 1von 5

#include

#include
#include
#include
#define
#define
#define
#define
#define
#define
#define

"stdio.h"
"stdlib.h"
"mpi.h"
"math.h"
matrix(x,y) matrix[x*width+y]
vec(x) vec[x]
vecin(x) vecin[x]
result(x) result[x]
ma(x,y) ma[x*width+y]
intsize sizeof(int)
floatsize sizeof(float)

int realp,p;
int width,col,row_per_pro;
float *matrix;
float *vec;
double starttime,finishprepare,finishcompute,finishall;
MPI_Status status;
FILE *fin;
/*
???: free_all
??:??????????????????
??:????????????ma,result,vecin
??:????
*/
void free_all(float *ma,float *result,float *vecin)
{
free(ma);
free(result);
free(vecin);
}
/*
???: main
??:???????????????,???????,??????????
??:argc????????
argv?????????????????
??:??0????????
*/
int main(int argc, char **argv)
{
int i,j,my_rank,group_size;
float sum;
float *ma;
float *result;
float *vecin;
MPI_Init(&argc,&argv);
MPI_Comm_size(MPI_COMM_WORLD,&group_size);
MPI_Comm_rank(MPI_COMM_WORLD,&my_rank);
p=group_size;
/*
???0??matrix,vec???????
???????????vec?matrix????
*/
if(my_rank==0)
{

/*
??????????
????dataIn.txt???width?col?
?????,???????
*/
starttime=MPI_Wtime();
fin=fopen("dataIn.txt","r");
fscanf(fin,"%d %d", &width, &col);
if (width!=(col-1))
{
printf("The input is wrong,check the input matrix width and the tota
l columns\n\n\n\n");
exit(1);
}
/*
???0??matrix?vec?????dataIn.txt???????
matrix ???width*width????????
vec???width???????
*/
matrix=(float *)malloc(floatsize*width*width);
vec=(float *)malloc(floatsize*width);
for(i = 0; i < width; i++)
{
for(j = 0; j < width; j++)
{
fscanf(fin,"%f", matrix+i*width+j);
}
fscanf(fin,"%f", vec+i);
}
/* ????dataIn.txt???????????? */
fclose(fin);
printf("The matrix and the vector has been read from file \"dataIn.txt\"
is: %d width\n ",width);
printf("The element of the matrix is as follows:\n");
for(i=0;i<width;i++)
{
printf("row %d\t",i);
for(j=0;j<width;j++)
printf("%f\t",matrix(i,j));
printf("\n");
}
printf("the element of the vector is as follows:\n");
for(i=0;i<width;i++)
{
printf("row %d is %f\n",i,vec(i));
}
}
/* ??0????width?,??????????????? */
MPI_Bcast(&width,1,MPI_INT,0,MPI_COMM_WORLD);
/*
?????????????,??????????row_per_pro???1
?????????????,?????????????
???????????????????????????
*/

row_per_pro=width/p;
if (width%p!=0)
row_per_pro++;
realp=0;
while(row_per_pro*realp<width)
realp++;
if(my_rank==0)
printf("now there is %d processors are working on it and %d rows per pro
cessors\n",realp,row_per_pro);
/* ??????????????????????? */
vecin=(float *)malloc(floatsize*width);
ma=(float *)malloc(floatsize*row_per_pro*width);
result=(float *)malloc(floatsize*row_per_pro);
/* ???0??vec????????????vecin????? */
if (my_rank==0)
{
for(i=0;i<width;i++)
vecin(i)=vec(i);
free(vec);
}
MPI_Bcast(vecin,width,MPI_FLOAT,0,MPI_COMM_WORLD);
/* ???0??matrix????????????????? */
if (my_rank==0)
{
for(i=0;i<row_per_pro;i++)
for(j=0;j<width;j++)
ma(i,j)=matrix(i,j);
}
if (my_rank==0)
{
if(width%realp==0)
{
for(i=1;i<realp;i++)
MPI_Send(&(matrix(row_per_pro*i,0)),row_per_pro*width,MPI_FLOAT,
i,i,MPI_COMM_WORLD);
}
else
{
for(i=1;i<(realp-1);i++)
MPI_Send(&(matrix(row_per_pro*i,0)),row_per_pro*width,MPI_FLOAT,
i,i,MPI_COMM_WORLD);
MPI_Send(&(matrix(row_per_pro*(realp-1),0)),
(width-row_per_pro*(realp-1))*width,
MPI_FLOAT,(realp-1),(realp-1),MPI_COMM_WORLD);
}
free(matrix);
}
else
{
if (my_rank<realp)
{
if(width%realp==0)
MPI_Recv(ma,row_per_pro*width,MPI_FLOAT,0,my_rank,MPI_COMM_WORLD
,&status);

else
{
if(my_rank!=realp-1)
MPI_Recv(ma,row_per_pro*width,MPI_FLOAT,0,my_rank,MPI_COMM_W
ORLD,&status);
else
MPI_Recv(ma,(width-row_per_pro*(realp-1))*width,MPI_FLOAT,0,
realp-1,MPI_COMM_WORLD,&status);
}
}
}
/* ????????????,???????,???????? */
MPI_Barrier(MPI_COMM_WORLD);
finishprepare=MPI_Wtime();
/* ???????????????? */
if (my_rank==0)
{
for(i=0;i<row_per_pro;i++)
{
sum=0.0;
for(j=0;j<width;j++)
sum=sum+ma(i,j)*vecin(j);
result(i)=sum;
}
}
else
{
if(my_rank<(realp-1))
{
for(i=0;i<row_per_pro;i++)
{
sum=0.0;
for(j=0;j<width;j++)
sum=sum+ma(i,j)*vecin(j);
result(i)=sum;
}
}
else
{
if (my_rank<realp)
{
for(i=0;i<(width-row_per_pro*(realp-1));i++)
{
sum=0.0;
for(j=0;j<width;j++)
sum=sum+ma(i,j)*vecin(j);
result(i)=sum;
}
}
}
}
/* ??????????,???????? */
MPI_Barrier(MPI_COMM_WORLD);
finishcompute=MPI_Wtime();

/* ???????0 */
if (my_rank==0)
{
for(i=0;i<row_per_pro;i++)
vecin(i)=result(i);
for(i=1;i<(realp-1);i++)
MPI_Recv(&(vecin(i*row_per_pro)),row_per_pro,MPI_FLOAT,i,i,MPI_COMM_
WORLD,&status);
if(realp!=1)
{
MPI_Recv(&(vecin(row_per_pro*(realp-1))),
(width-row_per_pro*(realp-1)),
MPI_FLOAT,(realp-1),(realp-1),
MPI_COMM_WORLD,&status);
}
}
else
{
if (my_rank<realp)
{
if (my_rank!=(realp-1))
MPI_Send(result,row_per_pro,MPI_FLOAT,0,my_rank,MPI_COMM_WORLD);
else
MPI_Send(result,(width-row_per_pro*(realp-1)),MPI_FLOAT,0,(realp
-1),MPI_COMM_WORLD);
}
}
/* ???0??vecin???????? */
if (my_rank==0)
{
printf("the result is as follows:\n");
for(i=0;i<width;i++)
printf("row%d %f\n",i,vecin(i));
}
MPI_Barrier(MPI_COMM_WORLD);
finishall=MPI_Wtime();
/* ????????? */
if (my_rank==0)
{
printf("\n");
printf("Whole running time
= %f seconds\n",finishall-starttime);
printf("prepare time = %f seconds\n",finishprepare-starttime);
printf("Parallel compute time = %f seconds\n",finishcompute-finishprepar
e);
}
MPI_Barrier(MPI_COMM_WORLD);
MPI_Finalize();
free_all(ma,result,vecin);
return (0);
}

Das könnte Ihnen auch gefallen