C - scanf中的管道在从管道读取时似乎不起作用

时间:2014-02-01 11:12:40

标签: c fork pipe scanf

我编写了以下程序来了解管道如何在C中工作。但它没有产生预期的输出。我使用管道将父进程的stdout连接到子进程的stdin。我为此目的使用了printf和scanf。但是子程序似乎等待输入而不是使用scanf读取它。 该代码遵循这个问题。

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <stdlib.h>

int main(){

    int pipefd[2];  
    pipe(pipefd);   
    int pid = fork();   // --- fork here ---    

    if (pid == 0){  // child process
        printf("child process\n");  

        int a=0, b=0;   

        close(pipefd[1]);
        dup2(pipefd[0],0);
        close(pipefd[0]);

        scanf("%d%d", &a, &b);
        printf("%d%d", a, b);
        exit(0);    
    }

    else{   // parent process
        printf("parent process\n");

        close(pipefd[0]);
        dup2(pipefd[1],1);
        close(pipefd[1]);

        printf("%d%d", 1, 2);

        wait(NULL);
    }
    return 0;
}

预期产量: 父进程 儿童过程 12

实际输出: 父进程 儿童过程  

1 个答案:

答案 0 :(得分:3)

您需要刷新stdout,以便通过管道发送缓冲区。您可以通过添加fflush(stdout)

来实现
printf("%d%d", 1, 2);
fflush(stdout);

然后你还需要在输出的末尾添加一些空格(无关紧要),因为scanf将等待空格或EOF:

printf("%d%d ", 1, 2);
fflush(stdout);

另一种刷新输出并一次添加空格的方法可能是在输出中添加换行符:

printf("%d%d\n", 1, 2);

虽然这似乎有效,但我并不完全确定这是否可以冲洗管道。

然而,这仍然无法按预期工作,因为打印输出为12,由scanf解释为一个整数,scanf将再次无限期等待第二个整数。所以添加一个分隔符空格:

printf("%d %d ", 1, 2);
fflush(stdout);