使用管道将数组从子进程传递到父进程

问题描述 投票:0回答:1

我正在尝试发送一个大数组,其中一半的值由子进程计算,另一半由父进程计算。我希望父进程从子进程获取一半数组的计算值,并将两个进程的两个数组合并/连接在一起,这样我就有一个最终数组,它是子数组和父数组计算加在一起的乘积。我尝试仅使用管道方法。我当前的代码使用“虚拟”数组,它是子进程的确定数组计算。然后,该数组通过管道传递到父进程,这允许将父进程的 Test->iterations 数组结果全部添加到一起。该数组在名为 Test 的结构中定义,其格式为:

typedef struct{
int *iterations
int height;
int width;
int start;
int end;
} Test;

由于这是一个 2D 数组,因此迭代的大小为 Test->width * Test->height * sizeof(int))。我还使用块读取和写入函数发送数组,因为它是一个非常大的数组。 我的并行程序函数(生成两个进程的函数)遵循以下格式:

int main(){ Test t; t.height=1000; t.width=1000; if ((t->iterations = malloc(t->width * t->height * sizeof(int))) == NULL) { perror("Cannot allocate memory (iterations)"); exit(EXIT_FAILURE); } processes(Test *); } void processes(Test *){ int p2c[2], c2p[2]; int i,j,k; int half; int *dummy = malloc(Test->width*Test->height*sizeof(int)); if(dummy==NULL){ perror("Malloc Error"); exit(EXIT_FAILURE); } for (i = 0; i < Test->height; i++) { for (j = 0; j < Test->width; j++) { dummy[i * Test->width + j] = 0.0; } } half=Test->height >> 1; pipe(p2c); pipe(c2p); if(fork()==0){ Test->start=0; Test->end=half; Compute(Test); for(i=Test->start;i<Test->end;i++){ for(j=0;j<Test->width;j++){ dummy[i*Test->width+j]=Test->iterations[i*Test->width+j]; } } chwrite(c2p[WRITE], (char*)dummy, Test->width * half * sizeof(int), 2048); printf("Sending Iterations\n"); close(p2c[READ]); close(c2p[WRITE]); exit(EXIT_SUCCESS); } else{ Test->start=half; Test->end=Test->height; Compute(Test); sleep(1); chread(c2p[READ], (char*)dummy, Test->width * half * sizeof(int), 2048); printf("Reading Iterations\n"); wait(NULL); for(i=0;i<Test->height;i++){ for(j=0;j<Test->width;j++){ Test->iterations[i*Test->width+j]=dummy[i*Test->width+j]; } }
但是,当我这样做时,迭代数组充满了零。有什么问题以及如何解决这个问题?

我的chunk读写函数如下:

void chwrite(int fd, char *buf, int count, int chunksize){ int numChunks = (int)(count/chunksize); int remsize = count-numChunks*chunksize; int i, j; for(i=0,j=0; i<numChunks; j+=chunksize,i++){ write(fd, &(buf[j]), chunksize); } write(fd, &(buf[j]),remsize); } void chread(int fd, char *buf, int count, int chunksize){ int numChunks = (int)(count/chunksize); int remsize=count-numChunks*chunksize; int i,j; for(i=0,j=0; i<numChunks; j+=numChunks, i++){ read(fd, &(buf[j]),chunksize); } read(fd, &(buf[j]) ,remsize); }
    
arrays c multiprocessing pipe fork
1个回答
0
投票

chwrite

chread
函数不会检查错误或不完整的写入或读取。另外,
chread
中存在一个错误,其中
j
增加了
numChunks
而不是
chunksize

for(i=0,j=0; i<numChunks; j+=numChunks, i++){ read(fd, &(buf[j]),chunksize); }
这里是 

chread

 的可能替代品,用于检查错误并允许不完整的读取。如果已读取任何内容,则返回读取的数量;如果未读取任何内容且要读取的数量为 0 或遇到文件结束条件,则返回 0;如果未读取任何内容且遇到错误,则返回 -1 :

int chread(int fd, char *buf, int count, int chunksize){ int done = 0; int rc = count ? -1 : 0; while (done < count) { if (chunksize > done - count) { chunksize = done - count; } rc = read(fd, &buf[done], chunksize); if (rc <= 0) { break; } done += rc; } return done ? done : rc; }
这是一个替换 

chwrite

 功能。它与 
chread
 类似,只是不检查文件结束条件。 (文件结束条件在写入时没有意义,并且正常运行的 
write
 调用不应返回 0,除非调用计数为 0。):

int chwrite(int fd, const char *buf, int count, int chunksize){ int done = 0; int rc = count ? -1 : 0; while (done < count) { if (chunksize > done - count) { chunksize = done - count; } rc = write(fd, &buf[done], chunksize); if (rc < 0) { break; } done += rc; } return done ? done : rc; }
    
© www.soinside.com 2019 - 2024. All rights reserved.