下面的代码显示了子进程如何写到管道结束,然后显示父进程如何从另一端读取 。 在我对代码进行实验后我注意到,只有在子进程终止之后,父进程才能读取数据。
有没有办法强制父进程到达前台并在孩子调用 write()后立即读取数据?有没有办法在不终止孩子的情况下读取数据?
#include <stdio.h> /* For printf */
#include <string.h> /* For strlen */
#include <stdlib.h> /* For exit */
#define READ 0 /* Read end of pipe */
#define WRITE 1 /* Write end of pipe */
char *phrase = "This is a test phrase.";
main(){
int pid, fd[2], bytes;
char message[100];
if (pipe(fd) == -1) { /* Create a pipe */
perror("pipe");
exit(1);
}
if ((pid = fork()) == -1) { /* Fork a child */
perror("fork");
exit(1);
}
if (pid == 0) { /* Child, writer */
close(fd[READ]); /* Close unused end */
write(fd[WRITE], phrase, strlen(phrase)+1);
close(fd[WRITE]); /* Close used end */
}
else { /* Parent, reader */
close(fd[WRITE]); /* Close unused end */
bytes = read(fd[READ], message, sizeof(message));
printf("Read %d bytes: %s\n", bytes, message);
close(fd[READ]); /* Close used end */
}
}
答案 0 :(得分:2)
你不正确。尝试在“子”部分关闭管道写入结束之前添加sleep(120)
调用并运行应用程序。
答案 1 :(得分:1)
第一种方法可以使用一些同步技术来完成。意味着孩子应该等到父母读取数据,或者在代码中父母终止。我在代码中添加了第二个管道,用于此同步。
写完后的孩子只是等待从那根烟斗中读取并在阅读时被阻止。
只有当父节点终止时,函数read才会返回(此处为0),因为现在read in child将获得文件结束通知,因为父节点退出后父节点中的管道写入结束。 (在父终止后,写端将自动关闭。我没有明确地添加它)
您的第二个要求
I also want the parent to read the data immediately after the child whites to
the pipe.
为什么你认为这不会发生?应该总是有一些微小的时间滞后。
#include <stdio.h> /* For printf */
#include <string.h> /* For strlen */
#include <stdlib.h> /* For exit */
#define READ 0 /* Read end of pipe */
#define WRITE 1 /* Write end of pipe */
char *phrase = "This is a test phrase.";
main(){
int pid, fd[2], bytes;
char message[100];
int fd1[2];
char buffer[1];
int ret;
if (pipe(fd) == -1) { /* Create a pipe */
perror("pipe");
exit(1);
}
if (pipe(fd1) == -1) { /* Create a pipe */
perror("pipe");
exit(1);
}
if ((pid = fork()) == -1) { /* Fork a child */
perror("fork");
exit(1);
}
if (pid == 0) { /* Child, writer */
close(fd[READ]); /* Close unused end */
close(fd1[WRITE]);/*Close write end of the 2nd pipe*/
write(fd[WRITE], phrase, strlen(phrase)+1);
close(fd[WRITE]); /* Close used end */
/*For synchronisation let the child try to
read from the 2nd pipe.
The function read, will return 0 only when the
parent terminates and in this we are
not interested if at all anything read or not.
The read statement below, will return only if the
parent has terminated, thus ensures that the
child terminates only after the parent*/
ret = read(fd1[READ],buffer, 1);
}
else { /* Parent, reader */
close(fd[WRITE]); /* Close unused end */
close(fd1[READ]); /*Close read end of the 2nd pipe*/
bytes = read(fd[READ], message, sizeof(message));
printf("Read %d bytes: %s\n", bytes, message);
close(fd[READ]); /* Close used end */
}
}
答案 2 :(得分:0)
以下代码演示了在孩子将内容写入管道后,父母可以读取管道的情况。不需要子进程关闭管道或终止。
#include <stdio.h> /* For printf */
#include <string.h> /* For strlen */
#include <stdlib.h> /* For exit */
#define READ 0 /* Read end of pipe */
#define WRITE 1 /* Write end of pipe */
char *phrase = "This is a test phrase.";
main(){
int pid, fd[2], bytes;
char message[100];
if (pipe(fd) == -1) { /* Create a pipe */
perror("pipe");
exit(1);
}
if ((pid = fork()) == -1) { /* Fork a child */
perror("fork");
exit(1);
}
if (pid == 0) { /* Child, writer */
close(fd[READ]); /* Close unused end */
write(fd[WRITE], phrase, strlen(phrase)+1);
sleep(10);
close(fd[WRITE]); /* Close used end */
sleep(20);
}
else { /* Parent, reader */
printf( "child ipd = %d\n\r", pid);
close(fd[WRITE]); /* Close unused end */
bytes = read(fd[READ], message, sizeof(message));
printf("Read %d bytes: %s\n", bytes, message);
close(fd[READ]); /* Close used end */
sleep(10);
}
}