使用管道实现聊天室的功能(有名pipe的应用)

本期主要介绍的是使用管道实现聊天室的功能(有名pipe的应用),整体的框架主要分为两个给部分:

第一部分:在主进程中创建从A到B的通信管道(这里AB分别代指通信双方),分别创建两个线程,一个是发送消息线程,一个是接收消息线程;
第二部分:在主进程中创建从B到A的通信管道(这里AB分别代指通信双方),分别创建两个线程,一个是发送消息线程,一个是接收消息线程;

首先来看一下第一部分(A to B)的一个头文件:

#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <string.h>
#include <pthread.h>
#include <unistd.h>
#include <stdlib.h>

接下来是两个线程以及主进程:

void *sendfun(void *arg)
{
	int ret;
	int fd = -1;
	char tmpbuff[1024] = {0};

	fd = open("./fifo1", O_WRONLY);		//打开管道
	if (-1 == fd)
	{
		perror("fail to open");
		return NULL;
	}


	while (1)
	{
		memset(tmpbuff, 0, sizeof(tmpbuff));	 //清除缓存区空间
		fgets(tmpbuff, sizeof(tmpbuff), stdin);  //从终端获取需要发送的消息
		write(fd, tmpbuff, strlen(tmpbuff));	 //写入管道
		if (!strcmp(tmpbuff, "q\n"))			 //发送q,对话结束
		{
			break;
		}
	}	
	close(fd);

	pthread_cancel(tid2);
	return NULL;
}

void *recvfun(void *arg)
{
	int ret;
	int fd;
	char tmpbuff[1024] = {0};

	fd = open("./fifo2", O_RDONLY);
	if (-1 == fd)
	{
		perror("fail to open");
		return NULL;
	}

	while (1)
	{
		read(fd, tmpbuff, sizeof(tmpbuff));
		if (!strcmp(tmpbuff, "q"))
		{
			break;
		}
		printf("RECV:%s\n", tmpbuff);
		memset(tmpbuff, 0, sizeof(tmpbuff));
	}

	close(fd);

	pthread_cancel(tid1);
	return NULL;
}
int main(int argc, const char *argv[])
{

	mkfifo("./fifo1", 0664);		//创建A端管道(A to B)

	pthread_create(&tid1, NULL, sendfun, NULL);	//创建发送线程
	pthread_create(&tid2, NULL, recvfun, NULL); //创建接收线程

	pthread_join(tid1, NULL);		//回收线程空间
	pthread_join(tid2, NULL);

	return 0;
}

接来看一下第二部分(B to A)的整个代码,由于两个代码非常相像,所以只要理解了第一个,第二个也是非常容易懂的,但是还是要对应着看哦!

#include <stdio.h>
#include <string.h>
#include <sys/types.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <unistd.h>
#include <pthread.h>
#include <stdlib.h>

pthread_t tid1;
pthread_t tid2;
void *sendfun(void *arg)
{
	int ret;
	int fd = -1;
	char tmpbuff[1024] = {0};

	fd = open("./fifo2", O_WRONLY);
	if (-1 == fd)
	{
		perror("fail to open");
		return NULL;
	}


	while (1)
	{
		memset(tmpbuff, 0, sizeof(tmpbuff));
		fgets(tmpbuff, sizeof(tmpbuff), stdin);
		tmpbuff[strlen(tmpbuff) - 1] = 0;
		write(fd, tmpbuff, strlen(tmpbuff));
		if (!strcmp(tmpbuff, "q"))
		{
			break;
		}
	}	

	pthread_cancel(tid2);

	return NULL;
}

void *recvfun(void *arg)
{
	int ret;
	int fd;
	char tmpbuff[1024] = {0};

	fd = open("./fifo1", O_RDONLY);
	if (-1 == fd)
	{
		perror("fail to open");
		return NULL;
	}

	while (1)
	{
		read(fd, tmpbuff, sizeof(tmpbuff));
		if (!strcmp(tmpbuff, "q\n"))
		{
			break;
		}
		printf("RECV:%s", tmpbuff);
		memset(tmpbuff, 0, sizeof(tmpbuff));
	}

	close(fd);
	pthread_cancel(tid1);

	return NULL;
}
int main(int argc, const char *argv[])
{


	mkfifo("./fifo2", 0664);


	pthread_create(&tid1, NULL, sendfun, NULL);
	pthread_create(&tid2, NULL, recvfun, NULL);

	pthread_join(tid1, NULL);
	pthread_join(tid2, NULL);

	return 0;
}

运行的结果如下:
在这里插入图片描述
本期的分享就到这里结束啦!希望大家能够掌握好线程以及管道的应用!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值