调用fork后程序重复输出起始内容的技术问题咨询
问题根源:标准输出的行缓冲机制
你看到的重复输出不是程序“回到起始位置”,而是printf的缓冲区在fork时被复制导致的。
默认情况下,标准输出(stdout)是行缓冲模式:当输出内容里没有换行符\n时,数据不会立刻写入终端,而是暂存在用户空间的缓冲区中。你的代码里printf("What??? ");没有换行,这段内容会留在缓冲区里。
当调用fork()时,子进程会完整复制父进程的地址空间,包括这个未刷新的缓冲区。之后父子进程各自执行后续代码,在退出时(或缓冲区满时)都会把自己缓冲区里的内容输出到终端,所以就出现了两次“What??? ”。
解决方法
有两种简单的方式可以避免这个问题:
- 手动刷新缓冲区:在调用
fork()之前,添加fflush(stdout);强制把缓冲区内容写入终端:
#include <unistd.h> #include <stdio.h> #include <time.h> int main(void) { int a = 10; printf("What??? "); fflush(stdout); // 刷新缓冲区 int *b = &a; printf("%p\t", b); int tm = time(0); int f = fork(); if (!f) *b = 15; else while(time(0) == tm); printf("%d %p\t", *b, b); }
- 给printf添加换行符:把
printf("What??? ");改成printf("What??? \n");,行缓冲遇到换行会自动刷新缓冲区,这样fork时缓冲区就没有残留内容了。
关于寄存器变量的探究
你提到的强制变量为寄存器(register关键字)和这个问题无关。fork的是整个进程的地址空间和上下文,即使变量被分配到寄存器,fork时也会将寄存器状态复制到子进程中。而当前问题的核心是IO缓冲的复制,和变量的存储位置没有关系。
内容的提问来源于stack exchange,提问作者Random
相关产品推荐
相关产品推荐

