Advertisement
Guest User

Untitled

a guest
Sep 21st, 2017
76
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 4.83 KB | None | 0 0
  1. #include "mpi.h"      // knjižnica MPI
  2. #include <stdio.h>
  3. #include <string.h>
  4. #include <stdlib.h>
  5. #include <math.h>
  6. #include <time.h>
  7.  
  8.  
  9.  
  10. #define EPSILON  0.001   /* natancnost */
  11. #define N 20 //velikost kvadrata
  12.  
  13.  
  14. int main(int argc, char *argv[])
  15. {
  16.     clock_t startclock, endclock;
  17.     double elapsed;
  18.     int my_rank;    // rank (oznaka) procesa
  19.     int num_of_processes;  // število procesov
  20.     int source;      // rank pošiljatelja
  21.     int destination;    // rank sprejemnika
  22.     int tag = 50;    // zaznamek sporoèila
  23.     char   ch;
  24.     int i, x, y;
  25.     double diff;
  26.     int skupnifinish;
  27.     double temp;
  28.     int dodatni;
  29.     int finish=1;
  30.     int *sizeproc;
  31.     int *velikost;
  32.     double mean;
  33.     double **T;
  34.     double **Tnew;
  35.     int size;
  36.     MPI_Status status;    // status sprejema
  37.     int stevilo_trakov=0;
  38.     int wherestart=0;
  39.     int whereend=0;
  40.     MPI_Datatype  DelnaMatrika;
  41.  
  42.     int n;
  43.     double h;
  44.     double x1, y1, rezultat, v, koncnaVsota=0;
  45.     double start, stop;
  46.  
  47.     num_of_processes=1;
  48.     MPI_Init(&argc, &argv);  // inicializacija MPI okolja
  49.     MPI_Comm_rank(MPI_COMM_WORLD, &my_rank);  // poizvedba po ranku procesa
  50.     MPI_Comm_size(MPI_COMM_WORLD, &num_of_processes);  // poizvedba po številu procesov
  51.     startclock=clock();
  52.     finish=1;
  53.     stevilo_trakov=0;
  54.     wherestart=0;
  55.     whereend=0;
  56.     sizeproc = (int *)malloc(num_of_processes * sizeof(int));
  57.     velikost = (int *)malloc(num_of_processes * sizeof(int));
  58.     T = (double **)malloc(sizeof(double *) * N);
  59.     Tnew = (double **)malloc(sizeof(double *) * N);
  60.     for(i=0; i<N; i++)
  61.     {
  62.         T[i] = (double *)malloc(sizeof(double) * N);
  63.         Tnew[i] = (double *)malloc(sizeof(double) * N);
  64.     }
  65.  
  66.     /* inicializacija robnih toèk */
  67.     for(i=0; i < N; i++)
  68.     {
  69.         Tnew[N-1][i] = 0.0;
  70.         Tnew[i][0] = Tnew[i][N-1] = Tnew[0][i] = 100.0;
  71.         T[N-1][i] = 0.0;
  72.         T[i][0] = T[i][N-1] = T[0][i] = 100.0;
  73.     }
  74.     /* inicializacija toèk v sredini */
  75.     mean = 0.0;
  76.     for(i=0; i < N; i++)
  77.     {
  78.         mean += T[i][0] + T[i][N-1] + T[0][i] + T[N-1][i];
  79.     }
  80.     mean /= (4.0 * N);
  81.     for(y=1; y < N-1; y++)
  82.     {
  83.         for(x=1; x < N-1; x++)
  84.         {
  85.             T[y][x] = mean;
  86.             Tnew[y][x] = mean;
  87.         }
  88.     }
  89.  
  90.  
  91.  
  92.     // ustvarimo nov tip mpi datatype, array velikosti N*stevilo_trakov
  93.     MPI_Type_contiguous(N, MPI_DOUBLE, &DelnaMatrika);
  94.     MPI_Type_commit(&DelnaMatrika);
  95.     temp=N/num_of_processes;
  96.     stevilo_trakov=floor(temp);
  97.     size=stevilo_trakov;
  98.     dodatni=N%num_of_processes;
  99.     wherestart = my_rank*size;
  100.     if(dodatni>0)
  101.     {
  102.         if(my_rank<dodatni)size++;
  103.         if(dodatni>my_rank) wherestart=wherestart+my_rank;
  104.         else wherestart=wherestart+dodatni;
  105.     }
  106.     whereend = wherestart+size;
  107.     if(my_rank==0)wherestart++;
  108.     if(my_rank+1==num_of_processes)whereend--;
  109.     fflush(stdout);
  110.  
  111.     MPI_Gather( &wherestart, 1, MPI_INT, sizeproc, 1, MPI_INT, 0, MPI_COMM_WORLD);
  112.     for(i=0;i<num_of_processes;i++)
  113.     {
  114.         if(i+1!=num_of_processes)
  115.         {
  116.             velikost[i]=sizeproc[i+1]-sizeproc[i];
  117.         }
  118.         else
  119.         {
  120.             velikost[i]=N-sizeproc[i]-1;
  121.         }
  122.         while(1)
  123.         {
  124.             diff = 0;
  125.             if(finish>0)
  126.             {
  127.                 for(x=wherestart; x <whereend; x++)
  128.                 {
  129.                     for(y=1; y < N-1; y++)
  130.                     {
  131.                         Tnew[x][y] = (T[x][y-1]+T[x][y+1]+T[x-1][y]+T[x+1][y])/4.0;
  132.                         if( fabs(Tnew[x][y]-T[x][y]) > diff )
  133.                         {
  134.                             diff = fabs(Tnew[x][y]-T[x][y]);
  135.                         }
  136.                     }
  137.                 }
  138.             }
  139.             if(my_rank>0)
  140.             {
  141.                 MPI_Send(Tnew[wherestart], 1, DelnaMatrika, my_rank-1,0, MPI_COMM_WORLD);
  142.             }
  143.             if(my_rank+1<num_of_processes)
  144.             {
  145.                 MPI_Send(Tnew[whereend-1], 1, DelnaMatrika, my_rank+1,0, MPI_COMM_WORLD);
  146.             }
  147.             if(my_rank>0)
  148.             {
  149.                 MPI_Recv(Tnew[wherestart-1], 1, DelnaMatrika, my_rank-1, 0, MPI_COMM_WORLD, &status);
  150.             }
  151.             if(my_rank+1<num_of_processes)
  152.             {
  153.                 MPI_Recv(Tnew[whereend], 1, DelnaMatrika, my_rank+1, 0, MPI_COMM_WORLD, &status);
  154.             }
  155.             if(diff<EPSILON)finish=0;
  156.             MPI_Allreduce (&finish, &skupnifinish, 1, MPI_INT, MPI_SUM, MPI_COMM_WORLD );
  157.             for(x=wherestart-1; x < whereend+1; x++)
  158.             {
  159.                 for(y=1; y < N-1; y++)
  160.                 {
  161.                     T[x][y] = Tnew[x][y];
  162.                 }
  163.             }
  164.             if( skupnifinish == 0) break;
  165.         }
  166.  
  167.  
  168.         if(my_rank>0)
  169.         {
  170.             for(i=wherestart; i < whereend; i++)
  171.             {
  172.                 MPI_Send(T[i], 1, DelnaMatrika, 0,0, MPI_COMM_WORLD);
  173.             }
  174.         }
  175.         else
  176.         {
  177.             for(x=1; x < num_of_processes; x++)
  178.             {
  179.                 for(i=sizeproc[x]; i <sizeproc[x]+velikost[x]; i++)
  180.                 {
  181.                     MPI_Recv(T[i], 1, DelnaMatrika, x, 0, MPI_COMM_WORLD, &status);
  182.                 }
  183.             }
  184.         }
  185.  
  186.         if(my_rank==0)
  187.         {
  188.             for(y=0; y < N; y++)
  189.             {
  190.                 for(x=0; x < N; x++)
  191.                 {
  192.                     printf(" %3.0f", T[y][x]);
  193.                 }
  194.                 printf("\n");
  195.             }
  196.         }
  197.         printf("\n");
  198.         /* sproscanje pomnilnika */
  199.         for(i=0; i<N; i++)
  200.         {
  201.             free(T[i]);
  202.             free(Tnew[i]);
  203.         }
  204.         free(T);
  205.         free(Tnew);
  206.         if(my_rank==0)
  207.         {
  208.             endclock=clock();
  209.             elapsed = ((double) (endclock - startclock) * 1000) / CLOCKS_PER_SEC;
  210.             printf("Za kvadrat velikosti : %d je bilo potrebno %d milisekund\n", N, (int)elapsed);
  211.         }
  212.     }
  213.     MPI_Finalize();
  214.     return 0;
  215. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement