程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> 關於C語言 >> MPI-2 並行IO的使用方法,mpi-2並行io

MPI-2 並行IO的使用方法,mpi-2並行io

編輯:關於C語言

MPI-2 並行IO的使用方法,mpi-2並行io


  寫的MPI程序需要用到並行IO來操作文件,但是搜遍了度娘都沒有找到多少關於並行IO函數的使用方法。最後在知網搜到了一些有用的論文,看了一下,感覺豁然開朗。

  MPI-1對文件的操作是使用綁定語言的函數調用來進行的,通常采用的是串行IO的讀寫方式,一般情況下是用一個主進程打開文件和讀取數據,然後分發給其他進程來處理,這種串行IO數據的通信量很大、效率較低。MPI-2實現了並行IO,允許多個進程同時對文件進行操作,從而避免了文件數據在不同進程間的傳送,對於需要密集文件操作的程序而言,簡直是一大福祉!

  並行IO可分為三種方法:指定顯式偏移量、獨立文件指針和共享文件指針,每種方式又可分為阻塞和非阻塞兩種情況。

  下面以讀寫一個二進制文件數組為例,闡述這三種方法的函數調用。下面的三個mian函數分別對應三種方法,讀取“data"二進制文件數組(文件內容:行數、列數、數組元素),讀取完整後由進程0輸出其讀取的數據以驗證讀取是否正確,最後所有進程將其讀取的數據寫入一個叫“data2"的二進制文件。怎麼來查看二進制文件的內容以驗證是否讀寫正確呢,或者說二進制文件和可讀內容的文本文件之間怎麼轉換呢?下面也給出簡單代碼。

  

  code:

  1 #include<stdio.h>
  2 #include<stdlib.h>
  3 #include<string.h>
  4 #include"mpi.h"
  5 
  6 #define BLOCK_LOW(rank,size,n)    ((rank)*(n)/(size))
  7 #define BLOCK_HIGH(rank,size,n)    (BLOCK_LOW((rank)+1,size,n)-1)
  8 #define BLOCK_SIZE(rank,size,n)    (BLOCK_HIGH(rank,size,n)-BLOCK_LOW(rank,size,n)+1)
  9 
 10 //並行IO:指定顯式偏移的文件操作
 11 int main(int argc, char *argv[])
 12 {
 13     int size,rank,i;
 14     int n,m;
 15     float *array;
 16     MPI_File fh;
 17     MPI_Status status;
 18     MPI_Init(&argc,&argv);
 19     MPI_Comm_rank(MPI_COMM_WORLD,&rank);
 20     MPI_Comm_size(MPI_COMM_WORLD,&size);
 21 
 22     MPI_File_open(MPI_COMM_WORLD,"data",MPI_MODE_RDONLY,MPI_INFO_NULL,&fh);
 23     MPI_File_read_at_all(fh,0,&n,1,MPI_INT,&status);    //從偏移量0處讀取
 24     MPI_File_read_at_all(fh,sizeof(int),&m,1,MPI_INT,&status);    //從偏移量1個int處讀取
 25     array=(float *)malloc(BLOCK_SIZE(rank,size,n)*m*sizeof(float));
 26     MPI_File_read_at_all(fh,2*sizeof(int)+BLOCK_LOW(rank,size,n)*m*sizeof(float),array,BLOCK_SIZE(rank,size,n)*m,MPI_FLOAT,&status);
 27     MPI_File_close(&fh);
 28 
 29     if(rank==0){
 30         printf("rank=%d: %d %d\n",rank,n,m);
 31         for(i=0;i<BLOCK_SIZE(rank,size,n)*m;i++){
 32             printf("% .0f",array[i]);
 33             if((i+1)%m==0)    putchar('\n');
 34         }
 35     }
 36 
 37     MPI_File_open(MPI_COMM_WORLD,"data2",MPI_MODE_CREATE|MPI_MODE_WRONLY,MPI_INFO_NULL,&fh);
 38     MPI_File_write_at_all(fh,0,&n,1,MPI_INT,&status);
 39     MPI_File_write_at_all(fh,sizeof(int),&m,1,MPI_INT,&status);
 40     MPI_File_write_at_all(fh,2*sizeof(int)+BLOCK_LOW(rank,size,n)*m*sizeof(float),array,BLOCK_SIZE(rank,size,n)*m,MPI_FLOAT,&status);
 41     MPI_File_close(&fh);
 42 
 43     MPI_Finalize();
 44     return 0;
 45 }
 46  
 47 /*
 48 //並行IO:獨立文件指針
 49 int main(int argc,char *argv[])
 50 {
 51     int size,rank,i;
 52     int n,m;
 53     float *array;
 54     MPI_File fh;
 55     MPI_Status status;
 56     MPI_Init(&argc,&argv);
 57     MPI_Comm_rank(MPI_COMM_WORLD,&rank);
 58     MPI_Comm_size(MPI_COMM_WORLD,&size);
 59 
 60     MPI_File_open(MPI_COMM_WORLD,"data",MPI_MODE_RDONLY,MPI_INFO_NULL,&fh);
 61     MPI_File_set_view(fh,0,MPI_INT,MPI_INT,"internal",MPI_INFO_NULL);    //設置絕對偏移量為0
 62     MPI_File_read_all(fh,&n,1,MPI_INT,&status);    //讀取後偏移量自動加1
 63     MPI_File_read_all(fh,&m,1,MPI_INT,&status);
 64     array=(float *)malloc(BLOCK_SIZE(rank,size,n)*m*sizeof(float));
 65     MPI_File_set_view(fh,2*sizeof(int)+BLOCK_LOW(rank,size,n)*m*sizeof(float),MPI_FLOAT,MPI_FLOAT,"internal",MPI_INFO_NULL);//重置偏移量
 66     MPI_File_read_all(fh,array,BLOCK_SIZE(rank,size,n)*m,MPI_INT,&status);
 67     MPI_File_close(&fh);
 68 
 69     if(rank==0){
 70         printf("rank=%d: %d %d\n",rank,n,m);
 71         for(i=0;i<BLOCK_SIZE(rank,size,n)*m;i++){
 72             printf("% .0f",array[i]);
 73             if((i+1)%m==0)    putchar('\n');
 74     
 75         }
 76     }
 77     
 78     MPI_File_open(MPI_COMM_WORLD,"data2",MPI_MODE_CREATE|MPI_MODE_WRONLY,MPI_INFO_NULL,&fh);
 79     MPI_File_set_view(fh,0,MPI_INT,MPI_INT,"internal",MPI_INFO_NULL);
 80     MPI_File_write_all(fh,&n,1,MPI_INT,&status);
 81     MPI_File_write_all(fh,&m,1,MPI_INT,&status);
 82     MPI_File_set_view(fh,2*sizeof(int)+BLOCK_LOW(rank,size,n)*m*sizeof(float),MPI_FLOAT,MPI_FLOAT,"internal",MPI_INFO_NULL); 
 83     MPI_File_write_all(fh,array,BLOCK_SIZE(rank,size,n)*m,MPI_FLOAT,&status);
 84     MPI_File_close(&fh);
 85 
 86     MPI_Finalize();
 87 }
 88 */
 89 
 90 /*
 91 //並行IO:共享文件指針
 92 int main(int argc,char *argv[])
 93 {
 94     int size,rank,i;
 95     int n,m;
 96     float *array;
 97     MPI_File fh;
 98     MPI_Status status;
 99     MPI_Init(&argc,&argv);
100     MPI_Comm_rank(MPI_COMM_WORLD,&rank);
101     MPI_Comm_size(MPI_COMM_WORLD,&size);
102 
103     MPI_File_open(MPI_COMM_WORLD,"data",MPI_MODE_RDONLY,MPI_INFO_NULL,&fh);
104     MPI_File_read_at_all(fh,0,&n,1,MPI_INT,&status);    //指定顯式偏移的讀取
105     MPI_File_read_at_all(fh,sizeof(int),&m,1,MPI_INT,&status);
106     array=(float *)malloc(BLOCK_SIZE(rank,size,n)*m*sizeof(float));
107     MPI_File_seek_shared(fh,2*sizeof(int),MPI_SEEK_SET);    //共享文件指針,偏移量是2個int
108     MPI_File_read_ordered(fh,array,BLOCK_SIZE(rank,size,n)*m,MPI_FLOAT,&status);    //按序讀取
109     MPI_File_close(&fh);
110 
111     if(rank==0){
112         printf("rank=%d: %d %d\n",rank,n,m);
113         for(i=0;i<BLOCK_SIZE(rank,size,n)*m;i++){
114             printf("% .0f",array[i]);
115             if((i+1)%m==0)    putchar('\n');
116     
117         }
118     }
119  
120     MPI_File_open(MPI_COMM_WORLD,"data2",MPI_MODE_CREATE|MPI_MODE_WRONLY,MPI_INFO_NULL,&fh);
121     MPI_File_write_at_all(fh,0,&n,1,MPI_INT,&status);    //指定顯式偏移的寫入
122     MPI_File_write_at_all(fh,sizeof(int),&m,1,MPI_INT,&status);
123     MPI_File_seek_shared(fh,2*sizeof(int),MPI_SEEK_SET);    //共享文件指針,偏移量是2個int
124     MPI_File_write_ordered(fh,array,BLOCK_SIZE(rank,size,n)*m,MPI_FLOAT,&status);    //按序寫入
125     MPI_File_close(&fh);
126 
127     MPI_Finalize();
128 }
129 */

 

 1 //將二進制數組文件轉換為文本文件。要求二進制文件的內容:行數 列數 數組元素
 2 #include <stdio.h>
 3 #include <stdlib.h>
 4 
 5 typedef float type;
 6 
 7 int main()
 8 {
 9     int i,j;
10     int n,m;
11     type **array;
12     FILE *fp;
13     fp=fopen("data","rb");
14     fread(&n,sizeof(int),1,fp);
15     fread(&m,sizeof(int),1,fp);
16 
17     array=(type **)malloc(n*sizeof(type *));
18     *array=(type *)malloc(n*m*sizeof(type));
19     for(i=1;i<n;i++)    array[i]=array[i-1]+m;
20 
21     fread(&array[0][0],n*m*sizeof(type),1,fp);  //注意不能是地址 array
22     fclose(fp);
23 
24     fp=fopen("data.txt","w");
25     fprintf(fp," %d %d\n",n,m);
26     for(i=0;i<n;i++){
27         for(j=0;j<m;j++)
28             fprintf(fp,"% f ",array[i][j]);
29         putc('\n',fp);
30     }
31     fprintf(stdout,"Successfully!\n");
32 }

 

 1 //將數組文本文件轉換為二進制文件。要求文本文件的內容:行數 列數 數組元素
 2 #include <stdio.h>
 3 #include <stdlib.h>
 4 
 5 typedef float type;
 6 
 7 int main()
 8 {
 9     int i,j;
10     int n,m;
11     type **array;
12     FILE *fp;
13     fp=fopen("data.txt","r");
14     fscanf(fp,"%d",&n);
15     fscanf(fp,"%d",&m);
16 
17     array=(type **)malloc(n*sizeof(type *));
18     *array=(type *)malloc(n*m*sizeof(type));
19     for(i=1;i<n;i++)    array[i]=array[i-1]+m;
20 
21     for(i=0;i<n;i++)
22         for(j=0;j<m;j++)
23             fscanf(fp,"%f",&array[i][j]);
24     fclose(fp);
25 
26     fp=fopen("data","wb");
27     fwrite(&n,sizeof(int),1,fp);
28     fwrite(&m,sizeof(int),1,fp);
29     fwrite(&array[0][0],n*m*sizeof(type),1,fp);  //注意不能是地址 &array
30     fclose(fp);
31     fprintf(stdout,"Successfully!\n");
32 }

 

  一個示例的文本文件數組data.txt:

  8 8
  1.000000 1.000000 1.000000 1.000000 1.000000 1.000000 1.000000 1.000000
  2.000000 2.000000 2.000000 2.000000 2.000000 2.000000 2.000000 2.000000
  3.000000 3.000000 3.000000 3.000000 3.000000 3.000000 3.000000 3.000000
  4.000000 4.000000 4.000000 4.000000 4.000000 4.000000 4.000000 4.000000
  5.000000 5.000000 5.000000 5.000000 5.000000 5.000000 5.000000 5.000000
  6.000000 6.000000 6.000000 6.000000 6.000000 6.000000 6.000000 6.000000
  7.000000 7.000000 7.000000 7.000000 7.000000 7.000000 7.000000 7.000000
  8.000000 8.000000 8.000000 8.000000 8.000000 8.000000 8.000000 8.000000

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved