параллельное программирование

Тема в разделе "Общие вопросы по С и С++", создана пользователем not dead, 12 май 2006.

Статус темы:
Закрыта.
  1. not dead

    not dead Гость

    помогите кто может!!!Валюсь по учебе
    Нужно подробное описание программы.Неважно рабочая ли она или нет..Она решает задачу теплопроводности с помощью распараллеливания..а именно создание виртуальной декартовой двумерной топологии ..Рассчетная область делится на I=J равных частей по осям х и у и происходит обмен межде процессорами..Данные ,рассчитанные в каждые в своей область,собираются в отдельные файлы ,которые потом обьединяются в один..Здесь представлена сама программа создания вирт.топологии и программа объединяющая файлы в один..
    Скажите пожалуйста что означает записьMPI_Comm COMM,MPI_File fh ,что такое fh ,зачем это нужно ,где и вкаких функциях это используется и для чего...
    Что делает функция MPI_File_open(MPI_COMM_SELF,fname,MPI_MODE_CREATE|MPI_MODE_RDWR,MPI_INFO_NULL,&fh); и что означают ее параметры и в какой части программы они используются... особенно MPI_COMM_SELF...И зачем этот комменикато нужен?
    Дайте пожалуйста подробное описание всех функций в программе и в частности функций типа MPI_*_*()
    Как происходит обмен данными в программе?
    HELP!!!!

    Код (Text):
    //рассчетная программа
    #include <stdlib.h>
    #include <stdio.h>
    #include <math.h>
    #include <mpi.h>
    #include <string.h>

    #define C(U) (1.0/(0.00225 - 0.000000000608*U*U))
    #define Ro(U) (7860.0 + 41500.0/U)
    #define Lambda(U) (1.45 + 0.023*U - 0.000002*U*U)
    #define U_XO(x, t, L) (340.0*x/L + (1.0 - x/L)*(300.0 + 700.0*t/T))
    #define U_XL(x, t, L) ((300.0 + 350.0*t/T)*(1.0 - x/L) + 340.0*x/L*exp(-0.125*t/T))
    #define U_OY(y, t, L) ( 300.0 + t/T*700.0/(1 + y/L) )
    #define U_LY(y, t, L) ( 340.0*exp( -0.125*t/T*y/L))
    #define U_XYO(x, y, L) ( (300.0 + 40.0*x/L)*(sin(3.14*y/L) + 1.0) )

    int funk_vyich();
    int funk_trans();
    int funk_fwrite();

    MPI_Comm COMM;
    MPI_File fh;

    int maxi, maxj, Hi,Hj,IDi,IDj;//кординаты процессора
    int gridrank;идентификатор процессора
    int NACHi,NACHj;
    int Uid,Rid,Lid,Did;//на границах блока

    int Numproc,Myid,h,N,st,end,I,J;
    int r[2],l[2],u[2],d[2];
    double *U1,*U2,*Temp,T;
    double start,Tau,dx,dy,dt,L;
    double *Rl,*Rr,*Rd,*Ru;
    double *Sl,*Sr,*Sd,*Su;

    int main (int argc,char* argv[])
    {
    int n,i,j;   
    double a_max;
    int Periods[2]= {0,0};//периодичность
    int Dims[2]  = {0,0};//количество процессоров по двум направлениям решетки
    int Coords[2] = {0,0};//координаты процессора
    char fname[100];

    FILE *out;
    FILE *file;

    //инициализация MPI
    MPI_Init(&argc,&argv);         
    MPI_Comm_size(MPI_COMM_WORLD,&Numproc);
    MPI_Comm_rank(MPI_COMM_WORLD,&Myid);

    //sprintf(fname,"/tmp/file_%d",Myid);
    sprintf(fname,"file_%d",Myid);

    MPI_File_open(MPI_COMM_SELF,fname,MPI_MODE_CREATE|MPI_MODE_RDWR,MPI_INFO_NULL,&fh);

    if (Myid == 0) file = fopen("OUT_L4.txt","a+");
    if (argc>2)
    {
    I = J = atoi(argv[1]);
    T = atof(argv[2]);
    }

    if(Myid==0)
    {
    printf("T = %4f I = J = %d\n",T,I);
    start = MPI_Wtime();//таймер
    }

    MPI_Bcast(&T, 1, MPI_DOUBLE, 0, MPI_COMM_WORLD);
    MPI_Bcast(&I, 1, MPI_INT, 0, MPI_COMM_WORLD);  
    MPI_Bcast(&J, 1, MPI_INT, 0, MPI_COMM_WORLD);  

    //параматры сетки
    L = 0.01;  
    dx = L/(I+1);
    dy = L/(J+1);
    a_max = .6237301272e-5;
    dt = 0.9*0.5/(1.0/dx/dx+1.0/dy/dy)/a_max;
    N = (int)(T/dt + 0.5);
    dt = T/N;

    MPI_Dims_create(Numproc,2,Dims);

    maxi = Dims[0];
    maxj = Dims[1];

    MPI_Cart_create(MPI_COMM_WORLD,2,Dims,Periods,1,&COMM);

    MPI_Comm_rank(COMM,&gridrank);

    MPI_Cart_coords(COMM,gridrank,2,Coords);
    IDi = Coords[0];   
    IDj = Coords[1];
    //координаты процессоов
    l[1] = Coords[1] - 1;
    l[0] = Coords[0];
    r[1] = Coords[1] + 1;
    r[0] = Coords[0];
    u[0] = Coords[0] - 1;
    u[1] = Coords[1];
    d[0] = Coords[0] + 1;
    d[1] = Coords[1];

    if(Coords[0]==0)
    Uid = -1;
    else

    MPI_Cart_rank(COMM,u,&Uid);

    if(Coords[0]==maxi-1)
    Did = -1;
    else       

    MPI_Cart_rank(COMM,d,&Did);

    if(Coords[1]==0)
    Lid = -1;
    else       

    MPI_Cart_rank(COMM,l,&Lid);

    if(Coords[1]==maxj-1)
    Rid = -1;  
    else           

    MPI_Cart_rank(COMM,r,&Rid);

    Hi = I/maxi;
    Hj = J/maxj;
    NACHi = Hi*IDi;  
    NACHj = Hj*IDj;  

    U1 = (double*)malloc((Hi+2)*(Hj+2)*sizeof(double));
    U2 = (double*)malloc((Hi+2)*(Hj+2)*sizeof(double));
    Sl = (double*)malloc((Hi+2)*sizeof(double));
    Sr = (double*)malloc((Hi+2)*sizeof(double));
    Sd = (double*)malloc((Hj+2)*sizeof(double));
    Su = (double*)malloc((Hj+2)*sizeof(double));
    Rl = (double*)malloc((Hi+2)*sizeof(double));
    Rr = (double*)malloc((Hi+2)*sizeof(double));
    Rd = (double*)malloc((Hj+2)*sizeof(double));
    Ru = (double*)malloc((Hj+2)*sizeof(double));

    //задаем начальные условия
    for (i=0;i<Hi + 2;i++) 
    {
    for (j=0;j<Hj + 2;j++)
    U1[i*(Hj+2) +j] = U_XYO(dx*(i + NACHi),dy*(j + NACHj),L);
    }                                          

    //цикл по времени
    for (n=0;n<N;n++)
    {
    Tau = dt*n; //шаг по времени

    //значения на границах
    if(IDi == 0) //верх
    for(j=0;j<Hj+2;j++)
    U1[j] = U_OY(dy*(j + NACHj),Tau,L);

    if(IDi == maxi - 1) //низ
    for(j=0;j<Hj+2;j++)            
    U1[(Hi + 1)*(Hj + 2) + j] = U_LY(dy*(j + NACHj),Tau,L);
    if(IDj == 0)//слева
    for(i=0;i<Hi+2;i++)            
    U1[i*(Hj+2)] = U_XO(dx*(i + NACHi),Tau,L);
    if(IDj == maxj - 1) //справа
    for(i=0;i<Hi+2;i++)            
    U1[i*(Hj+2) + (Hj + 1)] = U_XL(dx*(i + NACHi),Tau,L);

    funk_vyich();
    funk_trans();

    if (n>0 && n%1000==0) funk_fwrite();
    }

    //Tau = dt*N;
    //funk_napr();
    funk_fwrite();

    if(Myid==0)
    {
    printf("END\nTIME = %4.4lf (sec.)\n",MPI_Wtime() -start);
    fprintf(file,"np=%10d | I=J=%10d |T=%4.4f |Time=%2.3f (sec.)\n",IDi*IDj,I,T,MPI_Wtime() -start);
    fclose(file);
    }

    free(U1); free(U2); free(Sl); free(Sr);
    free(Sd); free(Su); free(Rl); free(Rr);
    free(Rd); free(Ru);

    MPI_File_close(&fh);
    MPI_Finalize();

    return 0;
    }

    //находит значения по пятиточечной схеме
    int funk_vyich()
    {
    int i,j;
    double l,c,r,d,u;
    Temp = U1; U1 = U2; U2 = Temp;
    for (i=1;i<Hi+1;i++)  
    {
    for (j=1;j<Hj+1;j++)
    {
    l = U2[(i-1)*(Hj+2) + j];
    r = U2[(i+1)*(Hj+2) + j];
    u = U2[i*(Hj+2) + (j+1)];
    d = U2[i*(Hj+2) + (j-1)];
    c = U2[i*(Hj+2) + j];  
    U1[(i)*(Hj+2) + j] = dt*((Lambda((r+c)/2.0)*(r-c) - Lambda( (c+l)/2.0)*(c-l))/(dx*dx) + (Lambda( (u+c)/2.0)*(u-c) - Lambda((c+d)/2.0)*(c-d))/(dy*dy)) /(Ro©*C©)+c;
    }
    }
    return 1;
    }


    int funk_trans()
    {
    int i,j;

    MPI_Status D;

    if (IDj%2 == 0 && IDj!=maxj-1) //процесор не правый
    {
    MPI_Send(U1+((Hj + 2) + Hj),  Hj, MPI_DOUBLE, Rid, gridrank+Rid+7777, COMM);     
    MPI_Recv(U1+((Hj + 2) + Hj + 1), Hj, MPI_DOUBLE, Rid, gridrank+Rid+77777, COMM, &D);
    }

    if (IDj%2 != 0 && IDj!=0)//не левый
    {
    MPI_Recv(U1+(Hj + 2),Hj, MPI_DOUBLE, Lid, gridrank+Lid+7777, COMM, &D);
    MPI_Send(U1+(Hj + 2 + 1),Hj, MPI_DOUBLE, Lid, gridrank+Lid+77777, COMM);     
    }
    if (IDj%2 != 0 && IDj!=maxj-1)
    {
    MPI_Send(U1+(Hj + 2 + Hj), Hj , MPI_DOUBLE, Rid, gridrank+Rid+17777, COMM);  
    MPI_Recv(U1+(Hj + 2 + Hj + 1),Hj, MPI_DOUBLE, Rid, gridrank+Rid+177777, COMM, &D);
    }

    if (IDj%2 == 0 && IDj!=0) {
    MPI_Recv(U1+(Hj + 2), Hj, MPI_DOUBLE, Lid, gridrank+Lid+17777, COMM, &D);
    MPI_Send(U1+(Hj + 2 + 1), Hj, MPI_DOUBLE, Lid, gridrank+Lid+177777, COMM);   
    }

    if (IDi%2 == 0 && IDi!=maxi-1)
    {
    MPI_Send(U1+(Hi*(Hj + 2) + 1),  Hi, MPI_DOUBLE, Did, gridrank+Did+71111, COMM);  
    MPI_Recv(U1+((Hi + 1)*(Hj + 2) + 1), Hi, MPI_DOUBLE, Did, gridrank+Did+711111, COMM, &D);
    }

    if (IDi%2 != 0 && IDi!=0)
    {
    MPI_Recv(U1 + 1,Hi, MPI_DOUBLE, Uid, gridrank+Uid+71111, COMM, &D);
    MPI_Send(U1 + (Hj + 2 + 1),Hi, MPI_DOUBLE, Uid, gridrank+Uid+711111, COMM);  
    }

    if (IDi%2 != 0 && IDi!=maxi-1)
    {
    MPI_Send(U1+(Hi*(Hj + 2) + 1),Hi, MPI_DOUBLE, Did, gridrank+Did+5555, COMM);     
    MPI_Recv(U1+((Hi + 1)*(Hj + 2) + 1),Hi, MPI_DOUBLE, Did, gridrank+Did+55555, COMM, &D);
    }

    if (IDi%2 == 0 && IDi!=0)
    {
    MPI_Recv(U1+1,Hi, MPI_DOUBLE, Uid, gridrank+Uid+5555, COMM, &D);
    MPI_Send(U1+(Hj + 2 + 1), Hi, MPI_DOUBLE, Uid, gridrank+Uid+55555, COMM);    
    }
    return 1;
    }

    //запись в файл для каждого процесса
    int funk_fwrite()
    {
    int i,j;
    int pp=10;   
    MPI_File_write(fh,&IDi,1,MPI_INT,NULL);
    MPI_File_write(fh,&IDj,1,MPI_INT,NULL);
    for (i=0;i<pp;i++)
    for (j=0;j<pp;j++)
    MPI_File_write(fh,U1+((1+(i*Hi)/pp)*(Hj + 2)+(1+(j*Hj)/pp)),1,MPI_DOUBLE,NULL);
    return 1;
    }


    //ПРОГРАММА - СБОРЩИК РЕЗУЛЬТАТОВ
    #include <stdio.h>
    #include <math.h>
    #include <stdlib.h>

    int main(int argc, char* argv[])
    {
    int n,ic,jc,id,i,j,np,ti=0,tj=0,t,blocks,s;
    char fname[100];
    double UG[100][100];

    FILE *f;

    if (argc<3) {np=2;t=1;}
    else {np =atoi(argv[1]);t=atoi(argv[2]);}  
    printf("%d files\n",np);
    blocks = 10*10*sizeof(double) + 2*sizeof(int);
    for (s=0;s<t;s++)
    {
    printf("reading time step %d\n",s);
    ti=0;tj=0;

    for (id=0;id<np;id++)
    {
    sprintf(fname,"file_%d",id);
    printf("position %d in <%s> opened, it contains ", blocks,fname);
    f=fopen(fname,"r");

    fseek(f,s*blocks, SEEK_SET);

    fread(&ic,sizeof(int),1,f);
    fread(&jc,sizeof(int),1,f);
    if (ic>ti) ti=ic;
    if (jc>tj) tj=jc;
    printf("(%d %d)",ic,jc);
    for (i=0;i<10;i++)
    for (j=0;j<10;j++)
    {
    fread(&(UG[ic*10+i][jc*10+j]),sizeof(double),1,f);
    }
    fclose(f);
    printf(", <%s> closed\n",fname);
    }
    ti++;tj++;
    printf("%d x %d\n",ti,tj);
    for (i=0;i<10*ti;i++)
    {
    for (j=0;j<10*tj;j++)
    printf("%8.2lf ",UG[i][j]);
    printf("\n");
    }
    }
    }
     
  2. ????

    ???? Гость

Загрузка...
Статус темы:
Закрыта.

Поделиться этой страницей