进程间通信之匿名管道通信

发布时间:2024年01月19日
每一次的努力都是自我成长的一步,坚持不懈的付出会铺就通向成功的道路。

进程间通信的介绍

数据传输:一个进程需要将它的数据发送给另一个进程
资源共享:多个进程之间共享同样的资源。
通知事件:一个进程需要向另一个或一组进程发送消息,通知它(它们)发生了某种事件(如进程终止
时要通知父进程)。
进程控制:有些进程希望完全控制另一个进程的执行(如Debug进程),此时控制进程希望能够拦截另
一个进程的所有陷入和异常,并能够及时知道它的状态改变。

进程间通信的发展

1、管道
2、System V进程间通信
3、POSIX进程间通信

进程间通信的分类

管道

匿名管道pipe
命名管道

system V ipc

System V 消息队列
System V 共享内存
System V 信号量

POSIX IPC

消息队列
共享内存
信号量
互斥量
条件变量
读写锁

进程间通讯的本质

就是让不同的进程看到相同的资源

资源?

资源就是具有特定格式的内存空间

这个资源谁提供的?

一般都是操作系统,这里有抛出一个问题那就是为什么两个进程间的通讯通讯的资源确实操作系统提供的呢这是因为我们可以想一下两个进程之间是具有独立性的如果说一个资源属于某个进程但是这个资源又作为了通信时的资源那么肯定会导致,破坏了进程间的独立性

管道

什么是管道

管道是Unix中最古老的进程间通信的形式。是一种基于文件的通信方式
我们把从一个进程连接到另一个进程的一个数据流称为一个“管道”如下图
在这里插入图片描述

匿名管道

#include <unistd.h>
功能:创建一无名管道
原型
int pipe(int fd[2]);
参数
fd:文件描述符数组,其中fd[0]表示读端, fd[1]表示写端返回值:成功返回0,失败返回错误代码
在这里插入图片描述

管道小总结

进程之间利用管道进行通信其实本质上来说就是利用一个属于操作系统的一个空间进行通信要注意这个空间必须属于操作系统而不属于某个进程因此我们可以知道其实本质就是进程在访问操作系统。

现在我给大家看一下管道通信的一个实列

#include <iostream>
#include <string>
#include <unistd.h>
#include <string.h>
#include <string>
#include <cstdio>
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>
using namespace std;
const int n = 2;
#define NUM 1024
void Write(int wfd)
{
    string a = "hello I am chile";
    char buffer[NUM];
    int num = 0;
    while (true)
    {
        buffer[0] = 0;
        snprintf(buffer, sizeof(buffer), "%s-%d-%d", a.c_str(), getpid(), num++);
        write(wfd, buffer, strlen(buffer));
        sleep(1);
    }
}
void Read(int rfd)
{
    char buffer[NUM];
    while (true)
    {
        int n = read(rfd, buffer, sizeof(buffer));
        if (n < 0)
        {
            return;
        }
        buffer[n] = 0;
        cout << "father get a message[" << getpid() << "]# " << buffer << endl;
    }
}
int main()
{
    int pipefd[2];
    int n = pipe(pipefd);
    if (n < 0)
    {
        return 1;
    }
    pid_t pid = fork();
    if (pid == -1)
    {
        return 2;
    }
    else if (pid == 0)
    {
        close(pipefd[0]);
        Write(pipefd[1]);
        close(pipefd[1]);
    }
    close(pipefd[1]);
    Read(pipefd[0]);
    pid_t rid = waitpid(pid, NULL, 0);
    if (rid < 0)
    {
        return 2;
    }
    close(pipefd[0]);
    return 0;
}

下图是运行的一个示意图
在这里插入图片描述
由于我们是死循环因此下面其实还在生成中大家可以动手操作一下。

文章来源:https://blog.csdn.net/m0_72433000/article/details/135682829
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。