【发布时间】:2023-02-26 12:00:16
【问题描述】:
作为C多处理器编程的实践,我一直在尝试制作一个可以使用文件作为进程间通信方式的程序。该程序的这一部分应该使用子进程来读取文件的内容并将它们复制到临时文件中,然后将它们从临时文件复制到输出文件中(最好逐行执行此操作)。问题是,在读取文件的所有行后似乎没有出现任何问题,循环只是回到第二行并再次开始,一次又一次......出于某种原因。
当我使用单个进程时它工作正常,但这不是我想要实现的目标。其他似乎有帮助的事情是用 write() 调用替换 fprintf() 调用(摆脱了输出文件中重复的行)。我想这个问题与 fgets 在我认为应该返回 NULL 时不返回 NULL 有关,但我不知道为什么会发生这种情况。我认为此时我从中得到的唯一教训是永远不要在循环内使用 fork() ,因为这几乎是我的问题和我发现的解决方案没有共同点的一件事,哈哈。以下是我正在使用的代码的一些细节:
图书馆:
#include
#include
#include
#include
#include
有问题的程序(在一些断言之后它在 main() 中):
//opening files with pathnames given as input, creates or overwrites output file
FILE* Nombres = fopen(argv[1],"r");
FILE* Apellidos = fopen(argv[2],"r");
FILE* Output = fopen(argv[3], "w");
//temp file with a fixed name so i can test around
char *tempname = "aaa.txt";
FILE* Tmp = fopen(tempname, "w+");
char linea[MAXIMA_LONGITUD_LINEA];
pid_t hijoid;
while(fgets(linea, MAXIMA_LONGITUD_LINEA,Nombres) != NULL){
printf("%s\n",linea);
Tmp = fopen(tempname, "w+"); //clear tempfile contents
hijoid = fork();
if(hijoid == 0){
write(fileno(Tmp),linea,strlen(linea));
exit(0);
}
else{
waitpid(hijoid,NULL,0);
rewind(Tmp);
if (fgets(linea, MAXIMA_LONGITUD_LINEA, Tmp) != NULL){
write(fileno(Output),linea,strlen(linea));
}
else{
printf("Line couldn't be read.\n");
}
}
}
提前致谢!
-
读取或写入文件时,数据缓冲在内存中。因此,一个进程在文件中看到的内容不一定是另一个进程在同一文件中看到的内容。
-
请注意,使用 fgets 您只能读取比缓冲区大小小 1 的内容,因为它总是在读取字符后添加 0 字节。
-
IMO,最好的方法是停止使用文件,并学习如何使用管道,因为这就是管道的用途。
-
写入文件时,在需要读者查看时使用
fflush()
刷新缓冲区。