文档章节

Head First C 第十章 进程间通信 创建管道

AlexTuan
 AlexTuan
发布于 2016/04/10 21:58
字数 889
阅读 66
收藏 5

Head First C 第十章 进程间通信 创建管道

我们已经可以通过重定向的方式,将子进程的输出重定向到文件,但我们想从进程中直接读取数据,如何使实现。

用管道连接进程

我们曾经用一个命令来连接进程,那就是管道:

  • python fake_rss.py | grep 'naruto'

可以用管道把一个进程的输出连接到另一个进程的输入。 管道两侧的命令是父子关系。

  1. 命令行创建了父进程。
  2. 父进程在子进程中克隆出了fake_rss.py脚本。
  3. 父进程用管道把子进程的输出连接到自己的输入。
  4. 父进程运行grep命令。

如果想在c代码中,而不是命令行中实现管道连接,该怎么做呢。

在浏览器中打开链接

我们要做以下两件事:

  1. 从python脚本的输出中获取链接
  2. 在浏览器中打开链接
如何创建管道

我们要在进程中创建两条新的流,用于管道的读取与写入。

数据流
0 stdin
1 stdout
2 stderr
3 管道读取端
4 管道写入端
  1. pipe()函数建立管道 因为子进程要把数据发送到父进程里,所以要用管道连接子进程的标准输入父进程的标准输出。 我们说过,每当打开数据流时,它都会加入描述符表。pipe()函数也是如此,它创建两条相连的数据流,并把它们加入描述符表中。 这样你只要从一条数据流中写入数据,就能从另一条数据流中读取
  2. 描述符存放在一个包含两个元素的数组中
    
    	int fd[2];
    	if (pipe(fd) == -1) {
    	    error("Can't create pipe");
    	}
    
  3. fd[1]写管道,fd[0]读管道 1. 在子进程中: - 需要关闭管道的fd[0]端 - 修改子进程的标准输出,让它指向fd[1]对应的数据流 因为子进程不会从管道中读取数据,子进程发送给标准输出的数据都会写入到管道中。 2. 在父进程中: - 需要关闭管道的fd[1]端,因为父进程不需要往管道中写入数据 - 修改父进程的标准输入,使其从描述符fd[0]的数据流中读取数据。
使用管道进行进程间通信
  1. 对于子进程的操作
    if (pid == 0) {
    
        dup2(fd[1], 1);
        close(fd[0]);
        execlp("python", "python", "./fake_rss.py", NULL);
    

} 2. 父进程的操作c dup2(fd[0], 0); close(fd[1]); char line[255]; while (fgets(line, sizeof(line) / sizeof(char), stdin)) { if (line[strlen(line) - 1] == '\n') line[strlen(line) - 1] = 0; printf("Got url :%s\n", line);

pid_t pid2 = fork();
if (pid2 == 0) {
  open_url(line);
}

} ``` 父进程要做的是: 1. 将标准输入stdin重定向到*fd[0]*的数据流。 2. 用一个while循环从stdin读入数据,判断条件为读入的结果(当执行脚本结束时会返回EOF,fgets()返回0,循环结束)。 3. 再fork()一次,用于创建多个子进程打开多个url。

有名管道

有名管道是基于文件的管道,也叫做FIFO(First In First Out)文件。 因为基于文件的管道有名字,所以两个进程只要知道管道的名字就能用它来通信,即使它们不是父子进程。 使用系统调用mkfifo()可以创建有名管道。

代码

process communication with pipe

© 著作权归作者所有

AlexTuan
粉丝 4
博文 27
码字总数 17966
作品 0
程序员
私信 提问
Head First C 第十章 进程间通信 闹钟

Head First C 第十章 进程间通信 闹钟 主要介绍一个函数,,的作用是:接收一个无符号整型参数,作为定时的秒数,系统会计时,时刻到达时,给进程发送一个SIGALRM的信号。 关于alarm() 注意 ...

AlexTuan
2016/04/17
40
0
Head First C 学习日志 第十章 进程间通信 输入输出重定向

Head First C 第十章 进程间通信 创建进程只是个开始如果你想控制运行中的进程,向进程发送数据或读取它的输出,该怎么办?通过进程间通信,进程可以合力完成某件工作。 进程内部一瞥 进程含...

AlexTuan
2016/04/09
61
0
Head First C 学习日志 第十章 进程间通信 捕捉信号

Head First C 第十章 进程间通信 捕捉信号 关于信号 信号是操作系统控制程序的方式,举个栗子,操作系统在看到用户输入了Ctrl+C时,就会向程序发送中断信号。信号映射表 | 信号 | 处理函数 ...

AlexTuan
2016/04/17
32
0
linux/unix下多进程间的通信

进程:进程是计算机运行的基本单位,利用多进程可以实现系统的多任务;但是,在多进程的任务中,进程之间的通信是比较麻烦的,因为,进程之间使用的是不同的进程空间,所以,编写多进程的系统...

陈小花与胡汉三
2013/12/07
1K
0
进程间通信 IPC interprocess communication

1,管道,FIFO 2, 信号 3,消息队列 4,共享类存 5.文件映射 6.socket 通信就是说进程之间传递数据。常见的方法有 pipe(管道),FIFO(命名管道),socket(套接字),SysVIPC 的 shm(共享内...

企图穿越
2010/05/02
1K
0

没有更多内容

加载失败,请刷新页面

加载更多

Spring Cloud Alibaba 实战(二) - 关于Spring Boot你不可不知道的实情

0 相关源码 1 什么是Spring Boot 一个快速开发的脚手架 作用 快速创建独立的、生产级的基于Spring的应用程序 特性 无需部署WAR文件 提供starter简化配置 尽可能自动配置Spring以及第三方库 ...

JavaEdge
今天
7
0
TensorFlow 机器学习秘籍中文第二版(初稿)

TensorFlow 入门 介绍 TensorFlow 如何工作 声明变量和张量 使用占位符和变量 使用矩阵 声明操作符 实现激活函数 使用数据源 其他资源 TensorFlow 的方式 介绍 计算图中的操作 对嵌套操作分层...

ApacheCN_飞龙
今天
7
0
五、Java设计模式之迪米特原则

定义:一个对象应该对其他对象保持最小的了解,又叫最小知道原则 尽量降低类与类之间的耦合 优点:降低类之间的耦合 强调只和朋友交流,不和陌生人说话 朋友:出现在成员变量、方法的输入、输...

东风破2019
昨天
23
0
jvm虚拟机结构

1:jvm可操作数据类型分为原始类型和引用类型,因此存在原始值和引用值被应用在赋值,参数,返回和运算操作中,jvm希望在运行时 明确变量的类型,即编译器编译成class文件需要对变量进行类型...

xpp_ba
昨天
5
0
聊聊nacos Service的processClientBeat

序 本文主要研究一下nacos Service的processClientBeat Service.processClientBeat nacos-1.1.3/naming/src/main/java/com/alibaba/nacos/naming/core/Service.java public class Service ex......

go4it
昨天
6
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部