Linux进程间通信(2)---无名管道和有名管道(超简单,有示例程序)
内容导读
互联网集市收集整理的这篇技术教程文章主要介绍了Linux进程间通信(2)---无名管道和有名管道(超简单,有示例程序),小编现在分享给大家,供广大互联网技能从业者学习和参考。文章包含3731字,纯文字阅读大概需要6分钟。
内容图文
![Linux进程间通信(2)---无名管道和有名管道(超简单,有示例程序)](/upload/InfoBanner/zyjiaocheng/933/db99e7cb199d41ac95d40bf5d255b14f.jpg)
管道是什么呢?
比如说有两个池塘A和B如果我先要A和B中的水可以相互流动,那么我们只需要在两个池塘间安放一条水管就可以了嘛!如果将A、B换成我们程序中的进程,那么使这两个进程通信的那根管子就叫管道。
管道可以分为两种:
无名管道
:用于父子进程间的通信。
有名管道
:用于任意两进程间的通信。
首先我们来看一下无名管道
管道不是有两端嘛,每一端都可以流入水和流出水,但是流入和流出是不是只能有一种情况呢。所以在无名管道中也一样,无名管道的两端,每一端都可以读和写。
若一端为读就要关闭他的写功能,另一端就只能为写关闭读功能
下面我们先看一下一个函数
#include <unistd.h>
int pipe(int pipefd[2])
作用:创建一个无名管道
参数:pipefd[2]为你自己定义的一个数组
返回值:成功 0,失败 -1;
pipefd[0]存储管道的读描述符
pipefd[1]存储管道的写描述符
好了接下来无名写一个小程序:
/*
创建一个管道,子进程读取管道内容,父进程写入管道内容
*/
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <stdlib.h>
#define N 1024
/*
1、子进程读 父进程写
2、先写才能读,所以保证父进程先完成写操作
*/
int main(void)
{
pid_t pid;
int pipe_fd[2];
int fd;
char date[]="wlecome the rose flower shop";
char buf[N];
if(pipe(pipe_fd)<0)
{
printf("pipe error\n");
}
pid=fork();
if(pid==0)//子进程
{
close(pipe_fd[1]);//子进程用于读,所以关闭写功能
sleep(3);//保证父进程运行完成,子进程只执行到关闭写功能
fd= read(pipe_fd[0],buf,sizeof(date));
if(fd>0)
{
printf("child progress read: %s\n", buf);
}
close(pipe_fd[0]);
exit(0);
}
if(pid>0)
{
close(pipe_fd[0]);//父进程写入,所以关闭读功能
sleep(1);//等待子进程关闭写功能
fd=write(pipe_fd[1],date,sizeof(date));
if(fd>0)
{
printf("father progress write: %s\n", date);
}
close(pipe_fd[1]);
sleep(2);
}
return 0;
}
/*
子进程:
close(pipe_fd[1]);
sleep(3);
父进程:
close(pipe_fd[0]);
sleep(1);
原因:假如子进程先运行(fork创建的进程父、子进程无法判断谁先运
行)子进程是读所以关闭写,sleep(3)让父进程运行,此时父进程运行,
先关闭读功能,还要保证写功能没有被子进程占用,这里子进程先运行上
来就关闭子进程的写功能了。假如父进程先运行,父进程先关闭读功能,
但是子进程没有关闭写功能,所以父进程sleep(1)延时1S.让子进程执行
完第一条程序。sleep(1)<sleep(3)
*/
看一下运行结果:
2s后
有名管道
有名管道你就可以理解为,有一个文件,A、B进程都可以访问,A可以向里面写数据,也可以读数据,B亦然。
话不多说,我们先来看一个函数
#include<sys/types.h>
#include<sys/stat.h>
int mkfifo(const char * pathname,mode_t mode);
参数:pathname: 文件名
mode:这个要深入研究的话比较复杂,我网上查了也很多
https://blog.csdn.net/superywf/article/details/73438465
这个博客里面是这样说的:
mkfifo()会依参数pathname建立特殊的FIFO文件,该文件必须不存在,而
参数mode为该文件的权限
有名管道读端:
#include <stdio.h>
#include <stdlib.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>
#include <string.h>
#define MYFIFO "/zxp_linux/myfifo"
int main(void)
{
int fd;
char buff[4096];
if(access(MYFIFO,F_OK)==-1)//检测文件是否存在,函数详解可以csdn一搜就有
{
if(mkfifo(MYFIFO,0666)<0)//创建有名管道
{
printf("error mkfifo\n");
exit(1);
}
}
fd=open(MYFIFO,O_RDONLY);//打开有名管道(文件)
if(fd<0)
{
printf("error open\n");
exit(1);
}
while(1)
{
memset(buff,0,sizeof(buff));
if(read(fd,buff,sizeof(buff)))
{
printf("read named_pipe %s\n", buff);
}
}
close(fd);
return 0;
}
写端口:
#include <stdio.h>
#include <stdlib.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <fcntl.h>
#include <unistd.h>
#define MYFIFO "/zxp_linux/myfifo"
int main(int argc,char *argv[])
{
int fd;
char buff[4096]={0};
if(argc<=1)
{
printf("error scanf\n");
printf("./write string\n");
}
sscanf(argv[1],"%s",buff);
fd=open(MYFIFO,O_WRONLY);
if(fd<0)
{
printf("error open\n");
exit(1);
}
if(write(fd,buff,sizeof(buff)));
{
printf("pipe write %s\n", buff);
}
close(fd);
return 0;
}
运行结果:
本文代码参考博客:
http://blog.csdn.net/mybelief321/article/details/9073895
https://blog.csdn.net/mybelief321/article/details/9075229
内容总结
以上是互联网集市为您收集整理的Linux进程间通信(2)---无名管道和有名管道(超简单,有示例程序)全部内容,希望文章能够帮你解决Linux进程间通信(2)---无名管道和有名管道(超简单,有示例程序)所遇到的程序开发问题。 如果觉得互联网集市技术教程内容还不错,欢迎将互联网集市网站推荐给程序员好友。
内容备注
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 gblab@vip.qq.com 举报,一经查实,本站将立刻删除。
内容手机端
扫描二维码推送至手机访问。