重定向(redirect)与管道(pipe)

来源:互联网 发布:开源行情软件 编辑:程序博客网 时间:2024/06/10 04:29

基本概念(具体参见APUE):
一个进程控制块中有多个文件描述符(file descriptor),如:
fd0:标准输入
fd1:标准输出
fd2:标准输错
fd3:自定义
fd4:自定义
...
每个文件描述符对应一个指向file table的指针。


重定向使用dup()/dup2()系统调用,
dup()的原型为:

int dup(int filedes)
函数返回当前可用的最小文件描述符,此描述符的file pointer与filedes的file pointer指向相同的file table。

dup2()的原型为:

int dup(int filedes, int filedes2)
函数指定filedes2与filedes的file pointer指向相同的file table。

下面是一个使用dup()的实例代码,功能为使进程的文件描述符1(标准输出)与文件"file1"的文件描述符的file pointer指向同一个file table,即将进程的标准输出写入到文件"file1"中也就是shell中常用的重定向'>'操作。
#include <stdio.h>#include <stdlib.h>#include <unistd.h>#include <fcntl.h>#include <string.h>int main(){  int fd;  if ((fd = open("file1", O_RDWR | O_CREAT | O_TRUNC, 00664)) < 0) {    perror("open");    exit(EXIT_FAILURE);  }  close(STDOUT_FILENO);  dup2(fd, STDOUT_FILENO);  char *buf = "I wrote this string to stdout.\n";  if (write(STDOUT_FILENO, buf, strlen(buf)) != strlen(buf)) {    perror("write");    exit(EXIT_FAILURE);  }  exit(EXIT_SUCCESS);}
总结:这两个函数的功能是使两个文件描述符的file pointer指向同一个file table,从而可以共享打开的文件。


管道使用pipe()系统调用,
原型为:

int pipe(pipefd[2])
其中:
pipefd[0]为管道的read端
pipefd[1]为管道的write端
下面是man 2 pipe的一个实例代码,功能为父进程向管道的write端写入argv[1],子进程从管道的read端逐个字符读入buf,然后输出到标准输出。

#include <sys/wait.h>#include <stdio.h>#include <stdlib.h>#include <unistd.h>#include <string.h>int main(int argc, char *argv[]){  int pipefd[2];  pid_t cpid;  char buf;  if (argc != 2) {    fprintf(stderr, "Usage: %s <string>\n", argv[0]);    exit(EXIT_FAILURE);  }  if (pipe(pipefd) == -1) { /× create a pipe */    perror("pipe");    exit(EXIT_FAILURE);  }  if ((cpid = fork()) < 0) {    perror("fork");    exit(EXIT_FAILURE);  }  else if (cpid == 0) { /* child process */    close(pipefd[1]); /* close write end of pipe */    while (read(pipefd[0], &buf, 1) == 1) /* read from read end of pipe */      write(STDOUT_FILENO, &buf, 1); /* write buf to STDOUT */    write(STDOUT_FILENO, "\n", 1);    close(pipefd[0]);    _exit(EXIT_SUCCESS);  }  else { /* parent process */    close(pipefd[0]); /* close read end of pipe */    write(pipefd[1], argv[1], strlen(argv[1])); /* write argv[1] to write end of pipe */    close(pipefd[1]);    wait(NULL);    exit(EXIT_SUCCESS);  }}

区别:重定向(redirect)主要是对同一个进程而言的,而管道(pipe)可用于进程间通信(IPC)。
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 小孩坐火车饮食怎么办 飞机托运了手机怎么办 飞机随身包超重怎么办 行李超过20公斤怎么办 飞机安检有钢板怎么办 飞机上拍照片怎么办? 飞机行李超重该怎么办 无法买机票出行怎么办 机票的保险发票怎么办 行李办理托运后怎么办 飞机托运超尺寸怎么办 机票无托运行李怎么办 飞机票不含托运怎么办 登机重量超了怎么办 随身行李超重了怎么办 国际航班没带护照怎么办 派出所不开户籍怎么办 做火车没身份证怎么办 2018年怎么办户籍证明 一岁宝宝护照怎么办 户籍证明开不了怎么办 信用卡提不了额怎么办 信用卡提额诈骗怎么办 信用卡提额失败怎么办 身份证证件号错误怎么办 东西落在飞机上怎么办 乘高铁忘记带身份证怎么办 身份证丢坐火车怎么办 苏州市民a卡怎么办 集体户口户口页怎么办 网上不能买火车票怎么办 集体户口离婚时怎么办 没户口本怎么办结婚证 酒店没带身份证怎么办 住酒店拍身份证怎么办 手机取火车票要怎么办 香港酒店没登记怎么办 住宿未带身份证怎么办 长期住酒店怎么办暂住证 港澳通行过期了怎么办 异地社保卡怎么办出来