IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 数据结构与算法 -> Linux——进程间通信(消息队列) -> 正文阅读

[数据结构与算法]Linux——进程间通信(消息队列)

消息队列

管道和共享内存:字节流数据
消息:数据报(类型+数据)
队列:优先级队列
可以指定类型来读取,在相同类型下,按照先进先出的顺序
在这里插入图片描述
消息队列的操作:

1.创建和访问一个消息队列
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/msg.h>

int msgget(key_t key, int msgflag);
  • key:某个消息队列的名字,给一个整型值即可
  • msgflag:有两个选项IPC_CREAT和IPC_EXCL,单独使用IPC_CREAT,如果消息队列不存在则创建之,如果存在则打开返回;单独使用IPC_EXCL是没有意义的;两个同时使用,如果消息队列不存在则创建之,如果存在则出错返回。
  • 返回值成功返回一个非负整数,即消息队列的标识码,失败返回-1
    2.把一条消息添加到消息队列中
int msgsnd(int msqid, const void *msqp, size_t msqsz, int msqflg);
  • msgid:由msgget函数返回的消息队列标识码
  • msqp:指针指向准备发送的消息
  • msqsz:消息结构中数据部分的大小,不包括类型大小
  • msgflg:默认为0
  • 返回值:成功返回0,失败返回-1

消息结构一方面必须小于系统规定的上限,另一方面必须以一个long int长整型开始,接受者以此来确定消息的类型

struct msgbuf 
{
	long mtye;    //消息类型,必须大于0
	char mtext[1]; //消息数据
}; 

3.从一个消息队列接受消息

ssize_t msgrcv(int msqid, void *msqp, size_t msqsz, long msqtyp, int msqflg);

参数:与msgsnd相同
返回值:成功返回实际放到接收缓冲区里去的字符个数,失败返回-1
如果指定的空间不能将消息的数据完全存储下来,则本次读取不成功

4.消息队列的控制函数

int msgctl(int msqid, int cmd, struct msqid_ds *buf);
  • msqid:由msgget函数返回的消息队列标识码
  • cmd:有三个可选的值

IPC_STAT 把msqid_ds结构中的数据设置为消息队列的当前关联值
IPC_SET 在进程有足够权限的前提下,把消息队列的当前关联值设置为msqid_ds数据结构中给出的值
IPC_RMID 删除消息队列

  • 返回值:成功返回0,失败返回-1

和之前一样,我们写两个程序,a向消息队列中写入数据,b从消息队列中读取数据。
在这里插入图片描述

在这里插入图片描述
完成下面的操作:

先连续发送三条消息:
在这里插入图片描述
然后,连续接收两个消息后发现消息队列中还剩下最后一条消息:
在这里插入图片描述
一旦消息队列中的消息被读完或者,读取不存在的消息,比如2号类型消息,那么终端显示就是阻塞状态

注意:在接收消息的时候,如果将消息类型改为0,不代表接收0号消息,而是不区分消息类型,直接接收,最后靠接受者自己使用

msg.h

#program once
typedef struct msgbuf
{
	long mtype;
	char mtext[128];
}MsgBuf;

发送

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<assert.h>
#include<unistd.h>

#include<sys/types.h>
#include<sys/ipc.h>
#include<sys/msg.h>

#include"msg.h"

int main(int argc,char *argv[])
{
	//argv[1]:type
	//argv[2]:data
	if(argc < 3)
	{
		printf("Please input type and data\n");
		exit(0);
	}
	
	MsgBuf mess;
	memset(&mess,0,sizeof(mess));
	sscanf(argv[1],"%d",&mss.mtype);
	strcpy(msss.mtext,argv[2]);
	
	int msgid = msgget((key_t)1234,IPC_CREAT | 0664);
	assert(msgid != -1);

	msgsnd(msgid,&mess,strlen(mess,mtext),0);
	
	exit(0);
}

接收(注意读取问题)

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<assert.h>
#include<unistd.h>

#include<sys/types.h>
#include<sys/ipc.h>
#include<sys/msg.h>

#include"msg.h"

int main(int argc,char *argv[])
{
	if(argc < 2)
	{
		printf("please input type\n");
		exit(0);
	}
	
	MsgBuf mess;
	memset(&mess,0,sizeof(mess));
	
	long type = 0;
	sscanf(argv[1],"%d",&type);
	
	int msgid = msgget((key_t)1234,IPC_CREAT | 0664);
	assert(msgid != -1);
	
	msgrcv(msgid,&mess,127,type,0);//改成5看看结果,消息截取
	printf("type:%d,data :%s\n",mess.mtype,mess.mtext);
	
	exit(0);
}

简单总结:
在这里插入图片描述

  数据结构与算法 最新文章
【力扣106】 从中序与后续遍历序列构造二叉
leetcode 322 零钱兑换
哈希的应用:海量数据处理
动态规划|最短Hamilton路径
华为机试_HJ41 称砝码【中等】【menset】【
【C与数据结构】——寒假提高每日练习Day1
基础算法——堆排序
2023王道数据结构线性表--单链表课后习题部
LeetCode 之 反转链表的一部分
【题解】lintcode必刷50题<有效的括号序列
上一篇文章      下一篇文章      查看所有文章
加:2022-03-06 13:22:01  更:2022-03-06 13:23:09 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/28 17:44:04-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码