多客户端与服务器结构

客户端

#include <head.h>
 
void insert_fd(struct pollfd* list, int* poll_len, struct pollfd client) {
	list[(*poll_len)++] = client;
}
 
int main(int argc, const char *argv[])
{
	short port = atoi(argv[1]);
 
	// 创建客户端套接字
	int client_fd = socket(AF_INET, SOCK_STREAM, 0);
 
	// 绑定ip和端口号
	struct sockaddr_in client_addr = {0};
	client_addr.sin_family = AF_INET;
	client_addr.sin_port = htons(port);
	client_addr.sin_addr.s_addr = inet_addr("0.0.0.0");
 
	// 连接
	int con = connect(client_fd, (struct sockaddr*)&client_addr, sizeof(client_addr));
	if (-1 == con) {
		printf("连接失败\n");
		return -1;
	}
 
	// 创建结构体数组
	struct pollfd list[10] = {0};
	int poll_len = 0;
 
	struct pollfd poll_scanf = {.fd = 0, .events = POLLIN, .revents = 0};
	struct pollfd poll_client = {.fd = client_fd, .events = POLLIN, .revents = 0};
 
	insert_fd(list, &poll_len, poll_scanf);
	insert_fd(list, &poll_len, poll_client);
 
	while (1) {
 
		poll(list, poll_len, -1);
 
		for (int i = 0; i < poll_len; i++) {
			if (list[i].revents == 0) {
				// 没有被激活
				continue;
			}
 
			if (list[i].fd == client_fd) {
				// 读取数据
				char buf[128] = "";
				int res = read(client_fd, buf, 128);
				if (res == 0) {
					continue;
				}
 
				printf("客户端读取到数据:%s\n", buf);
			}
 
			if (list[i].fd == 0) {
				char buf[128] = "";
				fgets(buf, 128, stdin);
				// 发送给服务器
				write(client_fd, buf, 128);
				//printf("输入数据:%s\n", buf);
			}
		}
	}
	return 0;
}

服务端

#include <head.h>
 
void insert_client(int* client_arr, int* client_arr_len, int client_fd) {
 
	client_arr[(*client_arr_len)++] = client_fd;
}
 
void remove_client(int* client_arr, int* client_arr_len, int client_fd) {
 
	int i, j, len = *client_arr_len;
	for (i = 0; i < len; i++) {
		if (client_arr[i] == client_fd) {
			break;
		}
	}
 
	for (j = i; j < len - 1; j++) {
		client_arr[j] = client_arr[j+1];
	}
	client_arr[j] = -1;
 
	(*client_arr_len)--;
}
 
int main(int argc, const char *argv[])
{
	short port = atoi(argv[1]);
 
	// 创建服务端套接字
	int server_fd = socket(AF_INET, SOCK_STREAM, 0);
 
	// 绑定ip和端口号
	struct sockaddr_in server_addr = {0};
	server_addr.sin_family = AF_INET;
	server_addr.sin_port = htons(port);
	server_addr.sin_addr.s_addr = inet_addr("0.0.0.0");
 
	bind(server_fd, (struct sockaddr*)&server_addr, sizeof(server_addr));
 
	// 监听
	listen(server_fd, 10);
 
	// 创建读列表
	fd_set readlist;
	// 初始化
	FD_ZERO(&readlist);
	// 将服务端套接字添加到读列表
	FD_SET(server_fd, &readlist);
	// 创建客户端文件描述符数组
	int client_arr[10] = {0};
	// 记录数组长度
	int client_arr_len = 0;
	// 记录最大文件描述符
	int max_fd = server_fd;
 
	while (1) {
		// 创建临时读列表,每次select监听到文件描述符会覆盖读列表
		fd_set templist = readlist;
 
		select(max_fd+1, &templist, NULL, NULL, NULL);
 
		if (FD_ISSET(server_fd, &templist)) {
			// 连接客户端
			struct sockaddr_in client_addr = {0};
			int len = sizeof(client_addr);
			int client_fd = accept(server_fd, (struct sockaddr*)&client_addr, &len);
 
			printf("客户端的ip地址:%s\n", inet_ntoa(client_addr.sin_addr));
			printf("客户端的端口号:%d\n", ntohs(client_addr.sin_port));
			max_fd = client_fd;
 
			// 将客户端文件描述符添加到读列表中
			FD_SET(client_fd, &readlist);
 
			// 将客户端文件描述符添加到文件描述符数组中
			insert_client(client_arr, &client_arr_len, client_fd);
		}
 
		// 遍历查找哪个客户端发送消息
		for (int i = 0; i < client_arr_len; i++) {
			if (FD_ISSET(client_arr[i], &templist)) {
				printf("%d\n", client_arr[i]);
				// 读取数据
				char buf[128] = "";
				int res = read(client_arr[i], buf, 128);
				if (4 == client_arr[i]) {
					// 给5发送数据
					write(5, buf, 128);
				}
				if (5 == client_arr[i]) {
					// 给4发消息
					write(4, buf, 128);
				}
				if (res == 0) {
					printf("客户端%d断开连接\n", client_arr[i]);
 
					// 从读列表中删除
					FD_CLR(client_arr[i], &readlist);
 
					// 从文件描述符数组中删除
					remove_client(client_arr, &client_arr_len, client_arr[i]);
					continue;
				}
				//printf("客户端%d发送的消息:%s\n", client_arr[i], buf);
 
			}
		}
	}
 
 
 
 
	return 0;
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值