进程间通信,管道、

一、基本概念

        进程间通信意味着两个不同进程之间可以交换数据,为了完成这一点,操作系统中提供两个进程可以同时访问的内存空间。

        进程不同于线程,不同线程使用同一片内存空间,但是不同进程具有不同的完全独立的内存空间。因此,要实现进程间通信就得考虑其他特殊方法。

二、通过管道实现进程间通信

        管道是不属于进程的资源,而是和套接字一样,属于操作系统的资源。所以两个不同进程可以通过管道进行通信。

#include <unistd.h>

int pipe(int filedes[2]);
/*
    成功返回 0 , 失败返回 -1.
    filedes[0] : 通过管道接收数据时使用的文件描述符, 即管道出口
    filedes[1] : 通过管道传输数据时使用的文件描述符, 即管道入口
*/

        管道的简易创建和使用。

        

#include <stdio.h>
#include <string.h>
#include <unistd.h>
#define BUF_SIZE 40

int main()
{
    char *buf = "who are you";
    char buff[BUF_SIZE];
    //定义管道出入口
    int guandao[2];
    //初始化管道
    pipe(guandao);
    //创建进程实现通信
    pid_t pid = fork();
    if(pid == 0)//子进程
    {
        write(guandao[1], buf, strlen(buf));
    }
    else{
        read(guandao[0], buff, sizeof(buff));
        puts(buff);
    }
    return 0;

}

运行如下:

三、进程间双向通信 

         注意,以上创建的父子进程虽然同时拥有管道出口和管道入口。但是数据进入管道之后就会成为无主数据,此时先读取管道数据的进程会获取无主的数据,其他进程后面再读取时将没有数据,所有,我们可以通过设置先后读取顺序(即延时读取)来实现双向通信。

        1、延时读取实现双向通信

#include <stdio.h>
#include <string.h>
#include <unistd.h>
#define BUF_SIZE 100

int main()
{
    char *buf = "who are you";
    char *buf1 = "I am your parent";
    char buff[BUF_SIZE];
    //定义管道出入口
    int guandao[2];
    //初始化管道
    pipe(guandao);
    //创建进程实现通信
    pid_t pid = fork();
    if(pid == 0)//子进程
    {
        write(guandao[1], buf, strlen(buf));
        close(guandao[1]);//使用之后及时关闭管道,能保证安全
        sleep(1);//延时1秒。等待数据被父进程先读取,再去读取父进程写入的数据
        read(guandao[0], buff, BUF_SIZE);
        printf("recv_from_parent: %s\n", buff);
        close(guandao[0]);
    }
    else{
        //父进程向读后写,读取之后管道已没有数据,不需要延时等待
        read(guandao[0], buff, BUF_SIZE);
        close(guandao[0]);
        printf("recv_from_son: %s\n", buff);
        write(guandao[1], buf1, strlen(buf1));
        close(guandao[1]);
        sleep(2);
    }
    return 0;

}

        程序执行情况如下:

 

         2、创建两个管道分别读取和写入

        上面延时可以实现双向通信,但是在使用过程中太过繁杂,且数据过大时,不方便计算延时使数据完全写入。所以推荐使用下面的创建两个管道的通信方式。

#include <stdio.h>
#include <string.h>
#include <unistd.h>
#define BUF_SIZE 40

int main()
{
    char *buf = "who are you";
    char buff[BUF_SIZE];
    //定义管道出入口
    int guandao[2];
    int guandao1[2];
    //初始化管道
    pipe(guandao);
    pipe(guandao1);
    //创建进程实现通信
    pid_t pid = fork();
    if(pid == 0)//子进程
    {
        write(guandao[1], buf, strlen(buf));
        close(guandao[1]);//使用之后及时关闭管道,能保证安全
        read(guandao1[0], buff, sizeof(buff));
        printf("recv_from_parent: %s\n", buff);
        close(guandao1[0]);
    }
    else{
        read(guandao[0], buff, sizeof(buff));
        close(guandao[0]);
        printf("recv_from_son: %s\n", buff);
        write(guandao1[1], "i am your parent", sizeof("i am your parent"));
        close(guandao1[1]);
    }
    return 0;

}

运行结果:

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值