我正在使用n = 2运行我的代码。我一直在尝试研究,但是当我尝试多次运行我的代码时,我不明白为什么我得到不同的输出。 在下面,您可以看到当我以n = 2运行时的输出,我的txt.file每行包含73个字符,并且由4行组成。
这是我第一次运行时的输出,是期望的输出
这是我第二次运行代码的输出
这是我第三次运行代码的输出
我不知道该怎么办才能防止在图像2中发生错误(在第二行中有\ 274),但是特别是出现错误时,我第三次运行代码。我必须使用MPI_Allocate吗?我可以提前释放矩阵吗?
这是我的代码:
#define MAXCHAR 73
#define MAXLENGTH 100
int main(int argc, char** argv) {
FILE *fp;
char* filename = "/Users/test.txt";
char *line = malloc(MAXCHAR);
char (*matA)[MAXCHAR] = NULL;
char str[MAXCHAR];
int rowCount, num_rows, i, my_id,
root_process,num_procs,rows_per_process;
MPI_Init(&argc, &argv);
root_process = 0;
/* find out MY process ID, and how many processes were started. */
MPI_Comm_rank(MPI_COMM_WORLD, &my_id);
MPI_Comm_size(MPI_COMM_WORLD, &num_procs);
// READ TXT FILE INTO DYNAMIC ARRAY
if(my_id == root_process){
fp = fopen(filename, "r");
if (fp == NULL){
printf("Could not open file %s",filename);
return 1;
}
//NUMBER OF lines
size_t count=1000;
rowCount=0;
while(getline(&line, &count, fp)!=-1) {
rowCount++;
}
//REWIND file
rewind(fp);
matA = malloc(rowCount*sizeof(matA));
i = 0;
while (fgets(str, MAXCHAR, fp) != NULL){
for (size_t j = 0; j < MAXCHAR; j++) {
if(str[j] == '\n'){
continue;
}
matA[i][j] = str[j];
}
i++;
num_rows = i;
}
fclose(fp);
}
// BCAST rowCount to Calculate rows each process will receive
MPI_Bcast(&rowCount, 1, MPI_INT, 0, MPI_COMM_WORLD);
rows_per_process = rowCount/num_procs;
char(*part_matrix)[MAXCHAR];
part_matrix = malloc(rows_per_process*sizeof(*part_matrix));
MPI_Scatter(&(matA[0][0]), rows_per_process*73, MPI_CHAR, &(part_matrix[0][0]), rows_per_process*73, MPI_CHAR, 0, MPI_COMM_WORLD);
printf("Process %i received %i rows:\n", my_id, rows_per_process);
// PRINTING
for (size_t i = 0; i < rows_per_process; i++) {
printf("PROCESS %i PRINTS LINE NUMBER %zu:\n", my_id, i);
for (size_t j = 0; j < MAXCHAR; j++) {
printf("%c", part_matrix[i][j]);
}
printf("\n" );
}
free(part_matrix);
MPI_Finalize();
return 0;
}
答案 0 :(得分:0)
我相信您的大部分问题都来自以下事实:
char (*matA)[MAXCHAR] = NULL;
matA = malloc(rowCount*sizeof(matA));
是分配数据的一种奇怪方法。
char *matA = NULL;
matA = malloc(rowCount*MAXCHAR*sizeof(char));
似乎更合理
相同
char *part_matrix=NULL;
part_matrix = (char*) malloc(rows_per_process*MAXCHAR*sizeof(char));
这样,您可以确保matA和part_matrix在内存中连续,并且在使用MPI函数时不会(在内存方面)不会造成损害。
MPI_Scatter simply becomes MPI_Scatter(matA, rows_per_process*MAXCHAR, MPI_CHAR, part_matrix, rows_per_process*MAXCHAR, MPI_CHAR, 0, MPI_COMM_WORLD);
我更改了您读取文件以进行工作的方式...
matA = (char*)malloc(rowCount*MAXCHAR*sizeof(char));
i = 0;
while (getline(&line, &count, fp)!=-1){
for (j = 0; j < MAXCHAR; j++) {
matA[i*MAXCHAR+j] = line[j];
}
i++;
num_rows = i;
}
因此,您有了test.txt
的完整示例,
AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA
BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB
CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC
DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD
主文件
#include <stdlib.h>
#include <stdio.h>
#include "mpi.h"
#define MAXCHAR 73
#define MAXLENGTH 100
int main(int argc, char** argv) {
FILE *fp;
char* filename = "test.txt";
char *line = (char*) malloc(MAXLENGTH);
char * matA= NULL;
char str[MAXCHAR];
int rowCount, num_rows, i, my_id,
root_process,num_procs,rows_per_process, j;
MPI_Init(&argc, &argv);
root_process = 0;
/* find out MY process ID, and how many processes were started. */
MPI_Comm_rank(MPI_COMM_WORLD, &my_id);
MPI_Comm_size(MPI_COMM_WORLD, &num_procs);
// READ TXT FILE INTO DYNAMIC ARRAY
if(my_id == root_process){
fp = fopen(filename, "r");
if (fp == NULL){
printf("Could not open file %s",filename);
return 1;
}
//NUMBER OF lines
size_t count=1000;
rowCount=0;
while(getline(&line, &count, fp)!=-1) {
rowCount++;
}
//REWIND file
rewind(fp);
matA = (char*)malloc(rowCount*MAXCHAR*sizeof(char));
i = 0;
while (getline(&line, &count, fp)!=-1){
for (j = 0; j < MAXCHAR; j++) {
matA[i*MAXCHAR+j] = line[j];
}
i++;
num_rows = i;
}
fclose(fp);
}
// BCAST rowCount to Calculate rows each process will receive
MPI_Bcast(&rowCount, 1, MPI_INT, 0, MPI_COMM_WORLD);
rows_per_process = rowCount/num_procs;
char *part_matrix = NULL;
part_matrix = (char*) malloc(rows_per_process*MAXCHAR*sizeof(char));
MPI_Scatter(matA, rows_per_process*MAXCHAR, MPI_CHAR, part_matrix, rows_per_process*MAXCHAR, MPI_CHAR, 0, MPI_COMM_WORLD);
if(my_id == root_process){
free(matA);
}
printf("Process %i received %i rows:\n", my_id, rows_per_process);
// PRINTING
for (i = 0; i < rows_per_process; i++) {
printf("PROCESS %i PRINTS LINE NUMBER %zu:\n", my_id, i);
for (j = 0; j < MAXCHAR; j++) {
printf("%c", part_matrix[i*MAXCHAR+j]);
}
printf("\n" );
}
free(part_matrix);
MPI_Finalize();
return 0;
}
mpirun -n 4返回
PROCESS 0 PRINTS LINE NUMBER 0:
AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA
Process 1 received 1 rows:
PROCESS 1 PRINTS LINE NUMBER 0:
BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB
Process 2 received 1 rows:
PROCESS 2 PRINTS LINE NUMBER 0:
CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC
Process 3 received 1 rows:
PROCESS 3 PRINTS LINE NUMBER 0:
DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD
mpirun -n 2返回
Process 0 received 2 rows:
PROCESS 0 PRINTS LINE NUMBER 0:
AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA AAAAAAAA
PROCESS 0 PRINTS LINE NUMBER 1:
BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB BBBBBBBB
Process 1 received 2 rows:
PROCESS 1 PRINTS LINE NUMBER 0:
CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC CCCCCCCC
PROCESS 1 PRINTS LINE NUMBER 1:
DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD DDDDDDDD