Advertisement
Guest User

Untitled

a guest
Nov 18th, 2019
108
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 8.74 KB | None | 0 0
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <time.h>
  4. #include "mpi.h"
  5.  
  6. #include <iostream>
  7. using namespace std;
  8.  
  9. int k=0;
  10. double temp;
  11. double a=0, b=1, c=2, nondiag, diag;
  12. int i,j,N=500,M=500,nonzero=200;
  13.  
  14. void createMatrix(double** Matrix){
  15.         for(i=0; i<N; i++) {
  16.                 for(j=0; j<nonzero; j++) {
  17.                         int val = rand()%N;
  18.                         while(val==i) {
  19.                                 val=rand()%N;
  20.                         }
  21.                         nondiag = a + rand() * (b-a) / RAND_MAX;
  22.                         Matrix[i][val] = nondiag;
  23.                 }
  24.         }
  25.  
  26.         for(i=0; i<N; i++) {
  27.                 diag = b + rand() * (c-b) / RAND_MAX;
  28.                 Matrix[i][i] = diag;
  29.         }
  30.  
  31. }
  32.  
  33. void printMatrix(double** Matrix){
  34.         for(i=0; i<N; i++) {
  35.                 for(j=0; j<M; j++) {
  36.                         printf("%f ",Matrix[i][j]);
  37.                 }
  38.                 printf("\n");
  39.         }
  40. }
  41.  
  42. void printMatrix_Q(double** Matrix, int rank){
  43.         printf("%d\n",rank);
  44.         for(i=0; i<N/2; i++) {
  45.                 for(j=0; j<M/2; j++) {
  46.                         printf("%f ",Matrix[i][j]);
  47.                 }
  48.                 printf("\n");
  49.         }
  50. }
  51.  
  52. void multiplyMatrixByVector(double** Matrix, double* Result, double* Vector){
  53.         double sum = 0;
  54.         for(i=0; i<N; i++) {
  55.                 for(j=0; j<M; j++) {
  56.                         sum+=Matrix[i][j]*Vector[j];
  57.                 }
  58.                 Result[i] = sum;
  59.                 sum = 0;
  60.         }
  61. }
  62.  
  63.  
  64. void generateVector(double* Vector){
  65.         for(i=0; i<N; i++) {
  66.                 Vector[i] = 1 + rand() * (5-1) / RAND_MAX;
  67.         }
  68. }
  69.  
  70. void createCRS(double** Matrix, double** CRS, int* CRS_ROWS){
  71.         int k = 0;
  72.         double temp;
  73.         for(i=0; i<N/2; i++) {
  74.                 for(j=0; j<M/2; j++) {
  75.                         temp = Matrix[i][j];
  76.                         if(temp!=0.0) {
  77.                                 CRS[k][0] = temp;
  78.                                 CRS[k++][1] = j;
  79.                         }
  80.                 }
  81.                 CRS_ROWS[i] = k;
  82.         }
  83. }
  84.  
  85. void decompressCRS(double** Matrix_validate_CRS, double** CRS, int* CRS_ROWS){
  86.         j=0;
  87.         for(i=0; i<N; i++) {
  88.                 int k = CRS_ROWS[i];
  89.                 for(j; j<k; j++) {
  90.                         Matrix_validate_CRS[i][(int)CRS[j][1]] = CRS[j][0];
  91.                 }
  92.         }
  93. }
  94.  
  95. void validateTwoMultipliedMatrixes(double* Matrix_one, double* Matrix_two, double* Matrix_three){
  96.         int errors = 0;
  97.         for(i=0; i<N; i++) {
  98.                 if(Matrix_one[i]!=Matrix_two[i] || Matrix_one[i]!=Matrix_three[i]||Matrix_two[i]!=Matrix_three[i])
  99.                         errors++;
  100.         }
  101.         if(errors==0)
  102.                 printf("Both multiplied matrixes are the same\n");
  103. }
  104.  
  105. void printCRS(double** CRS){
  106.         printf("\n\nCRS \n");
  107.         for(i=0; i<(M * (nonzero + 1)); i++) {
  108.                 for(j=0; j<2; j++) {
  109.                         printf("%lf ", CRS[i][j]);
  110.                 }
  111.                 printf("\n");
  112.         }
  113. }
  114.  
  115. void printResult(double* result){
  116.         for(i=0; i<N; i++)
  117.                 printf("%lf ",result[i]);
  118.  
  119.         printf("\n");
  120. }
  121.  
  122. void multiplyCRSbyVector(double **CRS, int* CRS_ROWS, double* Vector, double* multiply_result, int rank){
  123.         int vecshift=0,rowshift=0;
  124.         double sum=0.0;
  125.         j=0;
  126.  
  127.         if(rank==1)
  128.                 vecshift = N/2;
  129.         else if(rank==2)
  130.                 rowshift = N/2;
  131.         else if(rank==3) {
  132.                 rowshift = N/2;
  133.                 vecshift = N/2;
  134.         }
  135.         for(i=0; i<N/2; i++) {
  136.                 for(j; j<CRS_ROWS[i]; j++) {
  137.                         sum+=CRS[j][0] * Vector[vecshift+(int)CRS[j][1]];
  138.                 }
  139.                 multiply_result[i+rowshift] = sum;
  140.                 sum=0.0;
  141.         }
  142. }
  143.  
  144. void compareTwoResults(double* resultSeq, double* resultPar){
  145.         int errors=0;
  146.         for(i=0; i<N; i++) {
  147.                 if(resultSeq[i]!=resultPar[i])
  148.                         errors++;
  149.         }
  150.         printf("Erros: %d\n", errors);
  151. }
  152.  
  153. int main(int argc, char **argv)
  154. {
  155.  
  156.         int rank,ranksent,size,source,dest,tag,i,len;
  157.         char name[20];
  158.         len=20;
  159.  
  160.         MPI_Status status;
  161.         MPI_Init(&argc,&argv);
  162.         MPI_Comm_rank(MPI_COMM_WORLD,&rank);
  163.         MPI_Comm_size(MPI_COMM_WORLD,&size);
  164.  
  165.         double **Matrix, **CRS;
  166.         int *CRS_ROWS;
  167.         double *Vector;
  168.  
  169.         Matrix = (double**)malloc(N * sizeof(double*));
  170.         CRS = (double**)malloc(N * (nonzero+1) * sizeof(double*));
  171.         CRS_ROWS = (int*)malloc(N * sizeof(int));
  172.         Vector = (double*)malloc(N * sizeof(double));
  173.  
  174.         for(i=0; i<N; i++) {
  175.                 Matrix[i] = (double*)malloc(M*sizeof(double));
  176.         }
  177.  
  178.         for(i=0; i<(N*(nonzero+1)); i++) {
  179.                 CRS[i] = (double*)malloc(2*sizeof(double));
  180.         }
  181.  
  182.         double **p0,**p1,**p2,**p3;
  183.         double **dest_matrix;
  184.         double **crs_q;
  185.         int *crs_rows_q;
  186.         double *multiply_result;
  187.         double *result_all;
  188.         double *result_seq;
  189.  
  190.  
  191.  
  192.         p0 = (double**)malloc(N/2*sizeof(double*));
  193.         p1 = (double**)malloc(N/2*sizeof(double*));
  194.         p2 = (double**)malloc(N/2*sizeof(double*));
  195.         p3 = (double**)malloc(N/2*sizeof(double*));
  196.         dest_matrix = (double**)malloc(N/2*sizeof(double*));
  197.  
  198.         crs_q = (double**)malloc(N/2 * (nonzero+1) * sizeof(double*));
  199.         crs_rows_q = (int*)malloc(N/2 * sizeof(int));
  200.         multiply_result = (double*)malloc(N * sizeof(double));
  201.         result_all = (double*)malloc(N*sizeof(double));
  202.         result_seq = (double*)malloc(N*sizeof(double));
  203.  
  204.         for(i=0; i<N/2; i++) {
  205.                 p0[i] = (double*)malloc(M/2*sizeof(double));
  206.                 p1[i] = (double*)malloc(M/2*sizeof(double));
  207.                 p2[i] = (double*)malloc(M/2*sizeof(double));
  208.                 p3[i] = (double*)malloc(M/2*sizeof(double));
  209.                 dest_matrix[i] = (double*)malloc(M/2*sizeof(double));
  210.         }
  211.  
  212.         for(i=0; i<(N/2 * (nonzero+1)); i++) {
  213.                 crs_q[i] = (double*)malloc(2*sizeof(double));
  214.         }
  215.  
  216.         if(rank==0)
  217.         {
  218.                 createMatrix(Matrix);
  219.                 // printMatrix(Matrix);
  220.                 generateVector(Vector);
  221.                 multiplyMatrixByVector(Matrix,result_seq,Vector);
  222.  
  223.                 dest=0;
  224.                 tag=0;
  225.                 for(i=0; i<N/2; i++) {
  226.                         for(j=0; j<M/2; j++) {
  227.                                 dest_matrix[i][j] = Matrix[i][j];
  228.                                 p1[i][j] = Matrix[i][j+(N/2)];
  229.                                 p2[i][j] = Matrix[i+(M/2)][j];
  230.                                 p3[i][j] = Matrix[i+(N/2)][j+(M/2)];
  231.                         }
  232.                 }
  233.                 // MPI_Send(&(p1[0][0]),(N/2*M/2)*sizeof(double),MPI_DOUBLE,1,10,MPI_COMM_WORLD);
  234.                 // MPI_Send(&(p2[0][0]),(N/2*M/2)*sizeof(double),MPI_DOUBLE,2,10,MPI_COMM_WORLD);
  235.                 // MPI_Send(&(p3[0][0]),(N/2*M/2)*sizeof(double),MPI_DOUBLE,3,10,MPI_COMM_WORLD);
  236.                 // for(int d = 0; d < N/2; d++) {
  237.                 //         MPI_Send(&(p1[d][0]),M/2,MPI_DOUBLE,1,10,MPI_COMM_WORLD);
  238.                 //         MPI_Send(&(p2[d][0]),M/2,MPI_DOUBLE,2,10,MPI_COMM_WORLD);
  239.                 //         MPI_Send(&(p3[d][0]),M/2,MPI_DOUBLE,3,10,MPI_COMM_WORLD);
  240.                 // }
  241.  
  242.         }
  243.         MPI_Barrier(MPI_COMM_WORLD);
  244.  
  245.         if(rank==0) {
  246.                 MPI_Send(&(p1[0][0]),(N/2*M/2)+sizeof(double),MPI_DOUBLE,1,10,MPI_COMM_WORLD);
  247.                 MPI_Send(&(p2[0][0]),(N/2*M/2)+sizeof(double),MPI_DOUBLE,2,10,MPI_COMM_WORLD);
  248.                 MPI_Send(&(p3[0][0]),(N/2*M/2)+sizeof(double),MPI_DOUBLE,3,10,MPI_COMM_WORLD);
  249.         }
  250.         else{
  251.                 MPI_Recv(&(dest_matrix[0][0]),(N/2*M/2)+sizeof(double),MPI_DOUBLE,0,10,MPI_COMM_WORLD,&status);
  252.                 // for(int d = 0; d < N/2; d++) {
  253.                 //         MPI_Recv(&(dest_matrix[d][0]),M/2,MPI_DOUBLE,0,10,MPI_COMM_WORLD,&status);
  254.                 // }
  255.         }
  256.  
  257.         MPI_Bcast(Vector,N,MPI_DOUBLE,0,MPI_COMM_WORLD);
  258.  
  259.         // printMatrix_Q(dest_matrix,rank);
  260.  
  261.         createCRS(dest_matrix,crs_q,crs_rows_q);
  262.         MPI_Barrier(MPI_COMM_WORLD);
  263.  
  264.         multiplyCRSbyVector(crs_q,crs_rows_q,Vector, multiply_result,rank);
  265.         MPI_Barrier(MPI_COMM_WORLD);
  266.  
  267.  
  268.         MPI_Reduce(multiply_result,result_all,N,MPI_DOUBLE,MPI_SUM,0,MPI_COMM_WORLD);
  269.         MPI_Barrier(MPI_COMM_WORLD);
  270.  
  271.         if(rank==0) {
  272.                 compareTwoResults(result_seq,result_all);
  273.         }
  274.  
  275.         MPI_Finalize();
  276.         return(0);
  277. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement