管道(无名管道)和FIFO(有名管道)

共享单车需求预测问题:建模篇 机器学习训练营——机器学习爱好者的自由交流空间(qq群号:696721295) 在上一篇里,我们使用可视化的方法分析了“共享单车”的数据集,理解了特征(变量)之间的关系。我们将在本篇建立几个模型预测单车的需求量,并比较它们的预测效果。 随机森林填充法 首先,导入必需的库、训练集和检验集。 import pylab import calendar import numpy as np impor... 阅读详情

管道是最初的UnixIPC形式,但是因为管道没有名字,所以它们只能用于有亲缘关系的进程使用;进而有名管道(FIFO)应运而生,有名管道有一个路径名与之关联,所以允许无亲缘关系的进程访问同一个FIFO。

以下具体介绍管道:
管道的创建:管道由函数 int pipe(int fd[2]) 创建,提供一个单向数据流,该函数返回两个文件描述符,fd[0]和fd[1],前者用来打开读,后者用来打开写。

管道的用途:其典型用途就是为父子进程提供进程间通信手段; 其过程是由一个进程(它将成为父进程)创建一个管道后调用fork派生一个自身的副本,如图所示,父进程关闭这个管道的读出端,子进程关闭该管道的写入端,这样就在父子进程间形成了一个单向数据流。
这里写图片描述

这里写图片描述

前面所述都是半双工即单向的,只提供一个方向的数据流的管道,若需要一个双向的数据流,就得创建两个管道,每个方向一个,具体的实现步骤如下:
这里写图片描述
其图示如下:
这里写图片描述

该过程的一个小小的示例如下:

#include <iostream>
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <wait.h>

using namespace std;

int main()
{
    const char* parent_talk[] = {"Hello", 
                          "Can you tell me current data and time",
                          "I have to go, Bye",
                          NULL};
    const char* child_talk[] = {"Hi",
                         "No problem:",
                         "Bye",
                         NULL};

    int fd1[2], fd2[2];
    int res1 = pipe(fd1);
    int res2 = pipe(fd2);
    if(res1 < 0){
        printf("create pipe1 error\n");
        exit(1);
    }

    if(res2 < 0){
        printf("create pipe2 error\n");
        exit(1);
    }


    pid_t pid;
    pid = fork();

    if(pid == 0){
        close(fd1[1]);
        close(fd2[0]);
        char buffer[256];

        int i = 0;
        const char *child = child_talk[i];
        while(child){
            read(fd1[0], buffer, 256);
            printf("Parent:> %s\n", buffer);
            if(i == 1){
                time_t t;
                time(&t);
                sprintf(buffer, "%s%s", child, ctime(&t));
                write(fd2[1], buffer, strlen(buffer) + 1);
            }else{
                write(fd2[1], child, strlen(child) + 1);
            }

            ++i;
            child = child_talk[i];
        }

        close(fd1[0]);
        close(fd2[1]);
    }else if(pid > 0){
        char buffer[256];
        close(fd1[0]);
        close(fd2[1]);

        int i = 0;
        const char *parent = parent_talk[i];
        while(parent){
            write(fd1[1], parent, strlen(parent) + 1);
            read(fd2[0], buffer, 256);
            printf("Child:> %s\n", buffer);
            ++i;
            parent = parent_talk[i];
        }

        close(fd2[0]);
        close(fd1[1]);

        int status;
        wait(&status);
    }else{
        printf("create child error\n");
    }

    return 0;
}

该过程是创建了两个管道,父进程用一个管道的一端进行写,子进程用该管道的另一端进行读;子进程用另外一个管道的一端进行写,父进程用该管道的另一端进行读;从而通过管道完成父子进程之间的通信。

有名管道:
有名管道的创建: 其由函数 int mkfifo(const char *pathname, mode_t mode) 创建,该函数隐含指定权限为O_CREAT | O_EXCL,即就是mkfifo要么创建一个新的fifo,要么返回错误(因为所指定名字的fifo已经存在),若不想创建新的fifo,就直接用open打开一个已经存在的fiffo。

FIFO不能打开既用来读又用来写,因为FIFO是半双工的。

关于该FIFO的一个小小的示例如下:

//头文件
#include <iostream>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <string.h>

using namespace std;

const char *write_fifo_name = "write_fifo";
const char *read_fifo_name = "read_fifo";




//makefile文件
all:ser cli

ser:ser.cpp
    g++ ser.cpp -o ser

cli:cli.cpp
    g++ cli.cpp -o cli

.PHONY:clean
clean:
    rm ser cli


//服务器端的代码:

#include "utility.h"

int main()
{
    int write_fd, read_fd;

    int res = mkfifo(write_fifo_name, O_CREAT|O_EXCL|0600);
    if(res == -1){
        printf("mkfifo error.\n");
        exit(1);
    }

    write_fd = open(write_fifo_name, O_WRONLY);  //只写方式打开写管道
    if(write_fd == -1){    //以只写方式打开文件失败
        printf("open write fifo error.\n");
        unlink(write_fifo_name);   //解除文件的连接
        exit(1);
    }

    printf("waiting Client Connecct.....\n");
    while((read_fd = open(read_fifo_name, O_RDONLY)) == -1){   //一直等待,直到打开读文件成功
        sleep(1);
    }
    printf("client connect ok.\n");

    char sendbuf[256];
    char recvbuf[256];

    //进行服务器和客户端的通信
    while(1){
        printf("Ser:>");
        scanf("%s", sendbuf);   //输入服务器端的信息
        if(strncmp(sendbuf, "quit", 4) == 0){   //比较是否要退出,若服务器端请求退出,则先解除文件再退出
            unlink(write_fifo_name);  //解除文件
            write(write_fd, sendbuf, strlen(sendbuf) + 1);   //告诉客户端服务器端要退出
            break;
        }
        write(write_fd, sendbuf, strlen(sendbuf) + 1);  //将服务器端的信息写入发送缓冲区
        read(read_fd, recvbuf, 256);   //读取接收缓冲区的客户端发送的数据
        printf("Cli:>%s\n", recvbuf);
    }

    return 0;
}

//客户端的代码:
#include "utility.h"

int main()
{
    int write_fd, read_fd;

    int res = mkfifo(read_fifo_name, O_CREAT|O_EXCL|0600);
    if(res == -1){
        printf("make read fifo error.\n");
        exit(1);
    }       

    read_fd = open(write_fifo_name, O_RDONLY);   //只读方式打开写管道
    if(read_fd == -1){     //打开写管道失败,就无法读取服务器端发来的数据
        printf("server error.\n");
        unlink(read_fifo_name);   //断开写连接
        exit(1);
    }

    write_fd = open(read_fifo_name, O_WRONLY);   //以只写方式打开读管道,准备写入客户端要发送的数据
    if(write_fd == -1){
        printf("client connect server error.\n");
        exit(1);
    }

    char sendbuf[256];
    char recvbuf[256];
    while(1){
        read(read_fd, recvbuf, 256);    //客户端首先读取服务器端发来的数据
        printf("Ser:>%s\n", recvbuf);
        printf("Cli:>");
        scanf("%s", sendbuf);     //客户端写入自己要发送给服务器端的数据
        if(strncmp(sendbuf, "quit", 4) == 0){   //若是客户端要退出,则解除读管道,发送消息告诉服务器端客户端要退出
            unlink(read_fifo_name);   //解除连接
            write(write_fd, sendbuf, strlen(sendbuf) + 1);   //写入要退出的数据
            break;
        }
        write(write_fd, sendbuf, strlen(sendbuf) + 1);    //将数据写入到要发送给服务器端的缓冲区中
    }
    return 0;
}

最后来简单的说一说管道和有名管道的区别:
(1)有名管道可以进行无亲缘关系的进程间通信,但是管道只能用于有亲缘关系的进程间通信。
(2)创建并打开一个管道只需要pipe函数就够了,但是创建并打开FIFO需要在调用mkfifo后再调用open函数。
(3)管道在所有进程最终都关闭它之后自动消失,但是FIFO只有在调用unlink后才能从文件系统中删除。

浅谈功放PA的VBW 摘要:VBW(视频带宽)反映功放的宽带非线性特性和记忆效应,影响数字预失真(DPD)校正能力。其成因是功放管寄生参数(如Cshunt和Leff)形成低频并联谐振,导致供电臂阻抗增大,引发电压波动和记忆效应。测试方法包括双音IM3/IM5测试(以两侧IM3差≥3dB定义VBW)和魔T测试(通过S21曲线测量谐振频率)。改善措施主要是减小Leff,如采用双电源平衡馈电。VBW指标要求通常为魔T测试结果大于3倍信号带宽,以确保功放线性度。 阅读详情

相关推荐

Monocle2拟时轨迹基因模块的GO富集解析

本文详细解析了如何对Monocle2拟时分析中得到的基因表达模块进行GO富集分析。通过从热图对象中提取聚类模块,并利用clusterProfiler等工具进行功能注释,将抽象的基因表达时序模式转化为可解释的生物学功能主题,如免疫应答、细胞外基质组织等,从而深入理解细胞命运转变的驱动机制。

gpt4scribbler的博客 499

进程间的通信方式(二):管道Pipe和命令管道FIFO

1.概述        管道是最初的Unix IPC通信,可追溯到1973年的Unix第三版。尽管对于许多操作来说很有用,但它们的根本局限于没有名字,只能由亲缘关系的进程使用。这一点随着FIFO的加入System III Unix中得以改正。FIFO有时候称为命令管道(named pipe)。管道和FIFO都是使用通常的read和write函数访问的。        从技术上讲,自从可以在进程间传...

Master-TJ的个人博客 1527

105. replace( )函数

【目录】

weixin_63986098的博客 1万+

管道和FIFO(有名管道) (二)

全双工管道全双工管道需要双向通信,使用两个独立的数据流,故需要两个半双工管道实现实现全双工,每个方向一个。因为一个管道只存在一个缓冲区,写入管道的任何数据都添加到该缓冲区的末尾,从管道读出的都是取自该缓冲区开头的数据。#include &lt;sys/types.h&gt; #include &lt;unistd.h&gt; #include &lt;stdio.h&gt; #includ...

Hulk 412

怎么用phpstudy制作网站

随着实践的深入,你会逐渐掌握更多高级技巧和技术,让你的网站变得更加完善和吸引人。现在你已经成功设置了你的本地Web服务器环境,接下来我们将指导你如何利用这个环境来创建一个简单的PHP网页项目。为了使网站更加动态且功能丰富,我们需要学会如何让PHP脚本与MySQL数据库交互。为了让网站看起来更专业美观,可以考虑引入CSS样式表来定制网页布局及视觉效果。当你对本地开发的网站感到满意后,下一步就是将其发布到互联网上供他人访问了。让我们进一步扩展我们的网站,加入一个简单的用户注册与登录系统。

2401_87999399的博客 6574

Python小白也能玩转迅投QMT量化交易?手把手教你从安装到第一个策略

本文为零基础Python用户提供了上手迅投QMT量化交易平台的完整指南。从Python 3.6环境配置、QMT客户端获取安装,到核心概念讲解,并手把手教你编写并回测一个经典的双均线交易策略,帮助初学者快速迈出量化交易的第一步。

weixin_29103191的博客 763

管道(匿名管道与有名管道及两者区别)

无名管道(匿名管道)pipe: 1、它是半双工的(即数据只能在一个方向上流动),具有固定的读端和写端 2、只能用于具有亲缘关系的进程间通信(父子进程、兄弟进程等) 3、可以看成是一种特殊的文件,对它的读写也可以使用普通的read、write等函数,但它不是普通的文件,不属于任何文件系统,并且只能存在于内存中。 无名管道的一些特性: 读管道: 管道中有数据,read返回实际读到的字节数。 管道中无数据: ...

weixin_47179565的博客 2795

图形推理2-四大类六提示

图形推理笔记2

小y的学习笔记 6739

【命名管道】命名管道(FIFO)与进程通信

命名管道(FIFO)为我们提供了一个在不同进程间进行数据传递的简单而有效的途径。了解如何正确使用FIFO,避免常见的问题,比如权限设定和缓冲区管理。虽然有其复杂性,但是只要掌握了这些要点,我们就能够用好FIFO,为进程间的通信带来便利。

crr411422的博客 1037

Python爬虫实战——如何自动爬取百度搜索结果页面

本文介绍了如何使用Python爬虫抓取百度搜索结果页面的内容,包括如何构建搜索URL、获取页面HTML、解析内容、处理翻页以及存储数据等。通过该教程,您可以轻松实现批量抓取百度搜索结果,并为后续的数据分析和处理打下基础。希望本文能为您在爬虫开发、数据分析等领域提供帮助。如果您在实际应用过程中遇到问题,可以参考反爬虫应对策略,并结合实际需求进行调整。

2201_76125261的博客 1710

从入门到精通!Arduino 全栈开发深度指南

本文围绕 Arduino 开发撰写全攻略,从基础入门到高级应用层层递进。开篇介绍 Arduino 概念、优势及硬件家族,引导读者完成开发环境搭建与首个 LED 闪烁项目;深入讲解编程语法、I/O 控制及通信协议;详细阐述传感器、模块应用与调试优化技巧;最后以自定义库开发、低功耗设计等高级内容收尾,并给出综合项目案例与产品化思路。无论新手入门,还是开发者进阶,均可从中系统学习 Arduino 知识,掌握从理论到实践的全流程开发技能。

邓邓子的博客 2754

进程通信-管道

进程通信

lianxue420的博客 923

VB摄像头监控

该VB模块可对摄像头捕获的画面进行录像等,可在创建的窗口进行控制

Linux进程通信之无名管道(PIPE)和有名管道(FIFO)

进程间通信是什么? 进程间通信(IPC,InterProcess Communication)是指在不同进程之间传播或交换信息。简单说就是进程之间可以相互发送数据。 今天我们介绍管道:包括无名管道(PIPE)和有名管道(FIFO)。 无名管道(PIPE) 管道通常指无名管道,是 UNIX 系统IPC最古老的形式。 无名管道具有如下几个性质: 特点有: 1、它是半双工的(即数据只能在一个方向上流动),具有固定的读端和写端。 2、它只能用于具有亲缘关系的进程之间的通信(也是父子进程或者兄弟进程之间),实现依赖父

年年年的博客 5965

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

Probability and Statistics - 4th edition

Probability and Statistics - 4th edition

linux下进程通信(无名管道和有名管道FIFO)

一、什么是管道 管道是从unux继承过来的最早的IPC通讯方式之一,它有如下特点: 管道数据的读写是半双工的,即只能从写端写入,从读端读出; 管道数据不能重复读取,一旦调用read读取写入管道的数据,这段数据将永久从管道中移除,不能被其它进程获取; 管道有点类似于队列,允许用户向其中连续放入多条内容,然后可以逐条取出; 二、有名管道和无名管道 2.1、无名管道 无名管道的存在依赖于创建它的进程,当进程退出后,无名管道的资源也会自动释放; 无名管道通信只能用于具有亲缘关系的进程之间的通讯(有名管道没有这

weixin_39270987的博客 369

LinePhone3.2.7(android端最新版本) sip客户端

SIP客户端For android:LinePhone3.2.7(最新版本),官网地址:http://www.linphone.org/

linux 无名管道和有名管道fifo

无名管道简介:管道是半双工的,数据只能向一个方向流动,需要双方通信时,需要建立起两个管道。管道只能用于父子进程或者兄弟进程之间(具有亲缘关系的进程):管道对于管道两端的进程而言,就是一个文件,但它不是普通的文件,并且只存在于内存中。管道的读写规则:fifo先进先出规则,写入的内容每次都添加在管道缓冲区的末尾,并且每次都是从缓冲区的头部读出数据。无名管道相关函数说明:#include <unistd.

牛仔的blog 3336

无名管道(PIPE)和有名管道(FIFO)---@颜麓

无名管道(PIPE)和有名管道(FIFO) 1、无名管道(PIPE) 无名管道(匿名管道),是一种具有两个端点的通信通道,管道的一端用于读取管道内数据,另一端用于将数据写入到管道内。创建一个管道后,会获取一对文件描述符,用于读取和写入。匿名管道通常是用在父子进程之间,由父进程创建匿名管道,子进程会继承管道的读端和写端,实现通讯。 管道是单向的、先进先出的、无结构的字节流。写进程在管道的尾端写入数据,读进程在管道的首端读出数据。数据读出后将从管道中移走,其它读进程都不能再读到这些数据。管道提供了简单的流控制机

yanlu0514的博客 1952

linux 无名管道pipe和有名管道FIFO

1、管道(pipe) 管道是进程间通信的主要手段之一。一个管道实际上就是个只存在于内存中的文件,对这个文件的操作要通过两个已经打开文件进行,它们分别代表管道的两端。管道是一种特殊的文件,它不属于某一种文件系统,而是一种独立的文件系统,有其自己的数据结构。根据管道的适用范围将其分为:无名管道和命名管道。 ●     无名管道 主要用于父进程与子进程之间,或者两个兄弟进程之间。在linux系统

angle0615303的专栏 4500

3、操作系统——进程间通信(1)(无名管道(PIPE)和有名管道(FIFO))

操作系统——进程间通信(1)(无名管道(PIPE)和有名管道(FIFO))

weixin_45981798的博客 934

无名管道pipe和有名管道FIFO

定义: 1、管道是单向的,先进先出的,它把一个进程的输入和一个进程的输出连接在一起。 一个进程(写进程)在管道的尾部写入数据,另一个进程(读进程)在管道的头部读取数据 2、数据被一个进程读出后,将从管道中删除,其他进程将不能进行读取,当读空管道或在写入数据时管道已满将堵塞 3、管道包括有名管道和无名管道,无名管道只能用于父子进程之间的通信,有名管道可以用于一个系统中任意两个管道之间的通信

Ycx_lq的博客 537

Linux内核中无名管道pipe和有名管道fifo的分析

1、管道(pipe) 管道是进程间通信的主要手段之一。一个管道实际上就是个只存在于内存中的文件,对这个文件的操作要通过两个已经打开文件进行,它们分别代表管道的两端。管道是一种特殊的文件,它不属于某一种文件系统,而是一种独立的文件系统,有其自己的数据结构。根据管道的适用范围将其分为:无名管道和命名管道。 ●     无名管道 主要用于父进程与子进程之间,或者两个兄弟进程之间。在li

一个IT菜鸟的自白 967

进程间通信IPC之--无名管道(pipe)和有名管道(fifo)

转载于:http://blog.chinaunix.net/uid-25365622-id-3059840.html 每个进程各自有不同的用户地址空间,任何一个进 程的全局变量在另一个进程中都看不到,所以进程之间要交换数据必须通过内核,在内核中开辟一块缓冲 区,进程1把数据从用户空间拷到内核缓冲区,进程2再从内核缓冲区把数据读走,内核提供的这种机制称为进程间通信(IPC,InterPro

嵌入式软硬件设计/方案设计 761

有名管道(FIFO)和无名管道(PIPE)的特征

用于亲缘进程间 (比如父子进程、兄弟进程、祖孙进程……作不具有原子性,因此只能用于一对一的简单通信情形。写者同时进行写操作而数据不会互相践踏。,跟普通文件一样:使用统一的。,跟普通文件不同:不能使用。存储于普通文件系统之中。,具有写入原子性,支持多。有名字,因此无法使用。的数据,最先被读出来。,任何具有相应权限。

m0_72296639的博客 177

linux系统调用创建无名管道,linux 无名管道pipe和有名管道FIFO

1、管道(pipe)管道是进程间通信的主要手段之一。一个管道实际上就是个只存在于内存中的文件,对这个文件的操作要通过两个已经打开文件进行,它们分别代表管道的两端。管道是一种特殊的文件,它不属于某一种文件系统,而是一种独立的文件系统,有其自己的数据结构。根据管道的适用范围将其分为:无名管道和命名管道。●无名管道主要用于父进程与子进程之间,或者两个兄弟进程之间。在linux系统中可以通过系统调用建立起...

weixin_29822105的博客 831

(转)linux 无名管道pipe和有名管道FIFO

1、管道(pipe) 管道是进程间通信的主要手段之一。一个管道实际上就是个只存在于内存中的文件,对这个文件的操作要通过两个已经打开文件进行,它们分别代表管道的两端。管道是一种特殊的文件,它不属于某一种文件系统,而是一种独立的文件系统,有其自己的数据结构。根据管道的适用范围将其分为:无名...

chiloutao9982的博客 103

linux内核fifo接口,Linux内核中无名管道pipe和有名管道fifo的分析

最后,为了防止reader进程是因为收到信号量而退出,再给睡眠的writer进程一次机会,检查do_wakeup,如果为1就唤醒睡眠的writer进程。● pipe_write(fs/pipe.c)首先,与pipe_read相同,pipe_write采用互斥锁对临界区进行保护。写操作也放在死循环中,退出条件也与read相同。与pipe_read不同,writer进程不总是睡眠等待,在调用pi...

weixin_29535577的博客 411
上一篇: UNIX网络编程之线程浅析
下一篇: 拒绝服务型攻击
lm_123_456
博客等级 码龄11年 35粉丝 86原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值