文章内容
1. 管道简介
匿名管道:一般用于父子进程
FIFO管道/命名管道:一般用于两个独立的进程
通过命令的方式实现管道:
发送文件:send.cpp
#include<iostream>
using namespace std;
int main(int argc,char* argv[]){
for(int i=1;i<argc;++i){
cout << argv[i] << endl;
}
// cout << "Hello world" << endl;
}
接收文件:recv.cpp
#include<iostream>
using namespace std;
int main(){
string t;
string s;
while(cin >> s){
t+=s;
}
cout << "recv:" << t << endl;
}
结果为:
[root@foundation1 C++7.10]# g++ send.cpp -o send
[root@foundation1 C++7.10]# g++ recv.cpp -o recv
[root@foundation1 C++7.10]# ./send 1 2 3 a b c | ./recv
recv:123abc
通过命令行的输入实现管道的通信作用,send程序的输出变成了recv程序的输入
2. 匿名管道
2.1 单工管道
程序进程与Shell命令行进程单项通信
操作 | 程序 |
---|---|
打开管道 | FILE* f = popen("管道命令","读/写操作"); |
关闭管道 | pclose(管道指针); |
读取 | fread(用于接收数据的内存地址,每个元素大小,成员数,管道文件指针); |
写入 | fwrite(写入数据的内存地址,每个元素大小,成员数,管道文件指针); |
先需要编写好发送/接收文件
2.1.1 通过编码的方式实现管道
读取程序
#include<iostream>
using namespace std;
int main(){
FILE* f = popen("./send abcd 1234","r"); // 打开管道
if(NULL == f) perror("open pipe error");
char buff[256];
fread(buff,sizeof(char),256,f); // 读取
cout << buff << endl;
pclose(f); // 关闭文件
}
结果为:
[root@foundation1 C++7.10]# ./a.out
abcd
1234
[root@foundation1 C++7.10]# ./send abcd 1234
abcd
1234
写入程序
#include<iostream>
using namespace std;
int main(){
FILE* f = popen("./recv","w"); // 打开管道
if(NULL == f) perror("open pipe error");
const char str[] = "abcdefg";
fwrite(str,sizeof(char),sizeof(str),f); // 写入
pclose(f); // 关闭文件
}
结果为:
[root@foundation1 C++7.10]# ./a.out
recv:abcdefg
[root@foundation1 C++7.10]# echo abcdefg | ./recv
recv:abcdefg
执行 popen 时,会创建一个管道命令的子进程,父进程可以读出子进程的数据,也可以往子程序中写入数据
2.1.2 读写管道连接
#include <unistd.h>
#include <cstdio>
int main(int argc,char* argv[]){
const char* readcmd = argv[1]; // 第二个位置是读
const char* writecmd = argv[2]; // 第三个位置是写
char buffer[1024] = {
0}; // 初始化全零
FILE* readfile = popen(readcmd,"r");
fread(buffer,1,1024,readfile);
pclose(readfile);
readfile = NULL