您的位置:首页 > 其它

管道 PIPE

2016-04-21 09:00 267 查看
没错,就讲大家可能天天会用的“管道 | “,前者的输出是后者的输入。这里简单要提一点大家可能忽略了的一个有趣事实是,后者不用得到前者执行完毕才启动。更有趣的是,只要后者获取了足够的数据,前者便会停止执行。

grep 'colin' bigfile.txt | head


故而当 grep 在给定文件中找到含有给定字符串的 10行文字后,即可功成身退,因为那是 head 的全部所需。加入没有管道机制,那就只能这样:

grep 'colin' bigfile.txt > tmpfile; head tmpfile




管道

管道(pipe)
是所有Unix都愿意提供的一种进程间通信机制。管道是进程之间的一个单项数据流:一个进程写入管道的所有数据都由内核定向到另一个进程,另一个进程由此就可以从管道中读取数据。

管道被看作是打开的文件,但在已安装的文件系统中没有相应的映像。可以使用
pipe()
系统调用来创建一个新管道,这个系统调用会返回
一对文件描述符
; 然后进程通过
fork()
把这两个描述符传递给它的子进程,由此与子进程共享管道。进程可以在
read()
系统调用中使用第一个文件描述符从管道中读取数据,同样也可以在
write()
系统调用中使用第二个文件描述符相管道中写入数据。

eg:



示例

ctipc.h 后面系列都使用此头文件,所以这里include了一些多余的


#include <stdlib.h>
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <fcntl.h>
#include <semaphore.h>
#include <sys/mman.h>
/* #include <mqueue.h> */
#include <sys/fcntl.h>
/* mqueueh.h is for POSIX messaging queues, and is not available on OS X.  O_NONBLOCK has nothing to do with that, and is defined in fcntl.h */
#include <string.h>
#include <errno.h>
#include <pthread.h>
#include <signal.h>
#define FILE_MODE S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH
#define MAXLINE 1024


pipe.cpp


#define READFD 0
#define WRITEFD 1
#include "ctipc.h"
int main(int argc, char ** argv){
int pipe_fd[2], n, ret;
if(pipe(pipe_fd) < 0){
printf("create pipe error\n");
return 0;
}
if((ret = fork()) < 0){
printf("fork error \n");
return 0;
}
if( ret > 0){  //parent process
char buff[10240] = {0};
close(pipe_fd[WRITEFD]);
while(read(pipe_fd[READFD], buff, sizeof(buff))){
printf("<print from parent: %s> \n", buff);
}
printf("<print from parent: read end>\n");
close(pipe_fd[READFD]);
return 0;
}
else{ //child process
close(pipe_fd[READFD]);
char *info = "[printed in child process, hello world]";
write(pipe_fd[WRITEFD], info, strlen(info));
return 0;
}
return 0;
}


输出


shell> g++ pipe.cpp -o pipe.out
pipe.cpp:26:30: warning: conversion from string literal to 'char *' is deprecated
[-Wc++11-compat-deprecated-writable-strings]
char *info = "[printed in child process, hello world]";
^
1 warning generated.
shell>./pipe.out
<print from parent: [printed in child process, hello world]>
<print from parent: read end>


参考

SHELL重定向和管道的实现

Creating Pipes in C

Pipeline (Unix)
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: