网络编程并发服务器的应用
作业2:完成局域网CS模型,局域网内一个服务器,多个客户端连接一个服务器,完成局域网聊天(select函数,poll函数,完成TCP并发服务器)。
poll函数应用:
服务器部分代码:
//TCP服务器
#include<myhead.h>
#include<poll.h>
#define IP "192.168.60.68"
#define PORT 1028
#define BACKLOG 20
int main(int argc, const char *argv[])
{//AF_INET:IPv4通信int oldfd=socket(AF_INET,SOCK_STREAM,0);if(oldfd==-1){perror("socket");return -1;}int n=1;int res=setsockopt(oldfd,SOL_SOCKET,SO_REUSEADDR,&n,sizeof(n));if(res==0){printf("端口号快速复用成功\n");}//2、绑定IP和端口号struct sockaddr_in server={.sin_family=AF_INET,//IPv4.sin_port=htons(PORT),//端口号转为网络字节序.sin_addr.s_addr=inet_addr(IP),//IP地址};if(bind(oldfd,(struct sockaddr *)&server,sizeof(server))==-1){perror("bind");return -1;}//3、监听if(listen(oldfd,BACKLOG)==-1){perror("listen");return -1;}//4、接受客户端连接请求创建新的描述符用于通信//1-1设置结构体数组检测描述符发生事件struct pollfd fds[100];fds[0].fd=oldfd;//旧的套接字描述符检测数组中fds[0].events=POLLIN;int i;struct sockaddr_in client;socklen_t client_len=sizeof(client);int newfd;int count=1;while(1){int res=poll(fds,100,-1);if(res==-1){perror("poll");}if(res==0){printf("超时\n");}if(fds[0].revents==POLLIN){newfd=accept(oldfd,(struct sockaddr *)&client,&client_len);if(newfd==-1){perror("accept");return -1;}printf("%s发来连接请求\n",inet_ntoa(client.sin_addr));fds[count].fd=newfd;fds[count++].events=POLLIN;}for(i=1;i<100;i++){if(fds[i].fd>0&&fds[i].revents==POLLIN){char buff[1024];memset(buff,0,sizeof(buff));int len=recv(fds[i].fd,buff,sizeof(buff),0);if(len==0){printf("客户端下线\n");close(fds[i].fd);break;}printf("%s\n",buff);strcat(buff,"今天是周一");send(fds[i].fd,buff,sizeof(buff),0);}}}close(oldfd);return 0;
}
客户端代码部分:
//TCP客户端
#include<myhead.h>
#define IP "192.168.60.68"
#define PORT 1028
int main(int argc, const char *argv[])
{//1、创建套接字int oldfd=socket(AF_INET,SOCK_STREAM,0);if(oldfd==-1){perror("socket");return -1;}struct sockaddr_in server={.sin_family=AF_INET,.sin_port = htons(PORT),.sin_addr.s_addr =inet_addr(IP),};if(connect(oldfd,(struct sockaddr *)&server,sizeof(server))==-1){perror("connect");return -1;}char buff[1024];while(1){fgets(buff,sizeof(buff),stdin);send(oldfd,buff,sizeof(buff),0);int len=recv(oldfd,buff,sizeof(buff),0);if(len==0){perror("服务意外退出\n");break;}printf("接受服务器消息:%s\n",buff);}close(oldfd);return 0;
}
效果演示:

selsect函数部分:
代码效果:

服务器部分:
#include <myhead.h>
#define IP "192.168.60.68"
#define PORT 1028
#define BACKLOG 20int main(int argc, const char *argv[])
{//AF_INET:IPV4通信//SOCK_STREAM:TCP通信协议int oldfd = socket(AF_INET,SOCK_STREAM,0);//1、创建套接字if(oldfd==-1){perror("socket");return -1;}//2、绑定IP和端口号struct sockaddr_in server = {.sin_family = AF_INET,//IPV4.sin_port = htons(PORT),//端口号转为网络字节序.sin_addr.s_addr = inet_addr(IP),//IP地址};if(bind(oldfd,(struct sockaddr *)&server,sizeof(server))==-1){perror("bind");return -1;}//3、监听if(listen(oldfd,BACKLOG)==-1){perror("listen");return -1;}//4、接受客户端连接请求创建新的描述符用于通信struct sockaddr_in client;//接收客户端信息的结构体socklen_t client_len = sizeof(client);//计算出结构体大小//1-1定义容器放入描述符fd_set readfds,temp;//定义两个集合存放描述符FD_ZERO(&readfds);//清空集合内的内容FD_SET(0,&readfds);FD_SET(oldfd,&readfds);//描述符放入集合int maxfd = oldfd;//保留最大的描述符int newfd;while(1)//循环连入多个客户端{//1-2监视所有的描述符temp = readfds;int res = select(maxfd+1,&temp,NULL,NULL,NULL);//永久阻塞if(res==-1){perror("select");return -1;}if(res==0){printf("超时\n");continue;}//程序执行到此,说明某些描述符解除了阻塞 //1-3循环检测是谁发生了IO操作 int i;for(i = 0;i<=maxfd;i++){if(!FD_ISSET(i,&temp))//如果描述符不在容器中,继续下次循环查找{continue;}if(i==oldfd)//旧的描述符解除的阻塞{newfd = accept(i,(struct sockaddr *)&client,&client_len);FD_SET(newfd,&readfds);//产生新描述符代表新客户端,需要放入集合maxfd = newfd>maxfd?newfd:maxfd;//更新最大的描述符if(newfd==-1){perror("accept");return -1;}printf("%s发来连接请求\n",inet_ntoa(client.sin_addr));} else//0号描述符解除的阻塞,进行通话{//5、循环收发信息char buff[1024];memset(buff,0,sizeof(buff));int len = recv(i,buff,sizeof(buff),0);//0:阻塞发送 MSG_DONTWAIT:非阻塞if(len==0){close(i);//关闭新的描述符FD_CLR(i,&readfds);//移除退出的客户端描述符if(maxfd==i)//退出后,描述符个数减一{maxfd--;}printf("客户端下线\n");break;}printf("%s\n",buff);fgets(buff,sizeof(buff),stdin);send(i,buff,sizeof(buff),0);}}}close(oldfd);return 0;
}
客户端部分:
//TCP客户端
#include<myhead.h>
#define IP "192.168.60.68"
#define PORT 1028
int main(int argc, const char *argv[])
{//1、创建套接字int oldfd=socket(AF_INET,SOCK_STREAM,0);if(oldfd==-1){perror("socket");return -1;}struct sockaddr_in server={.sin_family=AF_INET,.sin_port = htons(PORT),.sin_addr.s_addr =inet_addr(IP),};if(connect(oldfd,(struct sockaddr *)&server,sizeof(server))==-1){perror("connect");return -1;}char buff[1024];while(1){fgets(buff,sizeof(buff),stdin);send(oldfd,buff,sizeof(buff),0);int len=recv(oldfd,buff,sizeof(buff),0);if(len==0){perror("服务意外退出\n");break;}printf("接受服务器消息:%s\n",buff);}close(oldfd);return 0;
}
相关文章:
网络编程并发服务器的应用
作业2:完成局域网CS模型,局域网内一个服务器,多个客户端连接一个服务器,完成局域网聊天(select函数,poll函数,完成TCP并发服务器)。 poll函数应用: 服务器部分代码&…...
数据结构——停车场管理问题
目录 1、问题描述2、逐步分析1)涉及操作2)代码实现 3、代码整合 1、问题描述 1、题目 设停车场内只有一个可停放n辆汽车的狭长通道,且只有一个大门可供汽车进出。汽车在停车场内按车辆到达时间的先后顺序,依次由北向南排列&#x…...
道品智能科技移动式水肥一体机:农业灌溉施肥的革新之选
在现代农业的发展进程中,科技的力量正日益凸显。其中,移动式水肥一体机以其独特的可移动性、智能化以及实现水肥一体化的卓越性能,成为了农业领域的一颗璀璨新星。它不仅改变了传统的农业灌溉施肥方式,更为农业生产带来了高效、精…...
AI实习--常用的Linux命令
一、基础命令 1. 切换到根目录。 cd ~ 2. 返回上一级目录。 cd .. 3. 查看当前目录下包括哪些文件和文件夹。 ls 4. 查看当前路径。 pwd 5. 将文件或文件夹剪切到目标目录下。 mv 文件所在路径 目标路径 6. 查看文本文件内容。 cat 文本文件名 7. 创建文件或文件夹…...
Python学习指南 + 谷歌浏览器如何安装插件
找往期文章包括但不限于本期文章中不懂的知识点: 个人主页:我要学编程(ಥ_ಥ)-CSDN博客 所属专栏: Python 目录 前言 Python 官方文档的使用 谷歌浏览器中如何安装插件 前言 在学习Python时,我们可能会出现这样的困惑&#x…...
研0找实习【学nlp】15---我的后续,总结(暂时性完结)
当下进展成果: nlptransformerpytorchhuggingfacebert简历环境配置表情识别文本分类 断更了快1个月,2个礼拜找实习,1个礼拜伤心,1个礼拜想我要干什么…… 承认自己的才疏学浅,了解了leetcode,和老师商量了…...
kylin麒麟银河桌面版操作系统安装部署
本文主要描述kylin麒麟银河桌面版操作系统的安装,该操作系统的安装源文件可以从kylin麒麟银河官方网站上下载,商业版本需要申请试用,开源版本可以直接下载使用。 如上所示,x86芯片处理器架构的请下载INTEL版本,华为海思…...
MyBatis插件原理及应用
🎮 作者主页:点击 🎁 完整专栏和代码:点击 🏡 博客主页:点击 文章目录 介绍<plugins>标签解析拦截器链的工作原理插件的应用场景MyBatis插件应用的四个组件InterceptorChain和Interceptor MyBatis框架…...
[M最短路] lc743. 网络延迟时间(spfa最短路+单源最短路)
文章目录 1. 题目来源2. 题目解析 1. 题目来源 链接:743. 网络延迟时间 相关链接: [图最短路模板] 五大最短路常用模板) 2. 题目解析 怎么讲呢,挺抽象的…很久没写最短路算法了。反正也是写出来了,但脱离了模板,把…...
MySQL 中的锁
MySQL 中的锁:全面解析与应用指南 在 MySQL 数据库的复杂世界里,锁是确保数据一致性、完整性以及并发控制的关键机制。无论是简单的小型应用还是复杂的企业级系统,深入理解 MySQL 中的锁对于优化数据库性能、避免数据冲突和错误都具有至关重要…...
【动手学电机驱动】STM32-FOC(8)MCSDK Profiler 电机参数辨识
STM32-FOC(1)STM32 电机控制的软件开发环境 STM32-FOC(2)STM32 导入和创建项目 STM32-FOC(3)STM32 三路互补 PWM 输出 STM32-FOC(4)IHM03 电机控制套件介绍 STM32-FOC(5&…...
【C++11】尽显锋芒
(续) 一、可变参数模板 C11支持可变参数模板,也就是说支持可变数量参数的函数模板和类模板,可变数目的参数被称 为参数包,存在两种参数包:模板参数包,表示零或多个模板参数;函数参数包:表示零…...
掌握控制流的艺术:Go语言中的if、for和switch语句
标题:掌握控制流的艺术:Go语言中的if、for和switch语句 在Go语言的编程世界中,控制流语句是构建程序逻辑的基石。if语句、for循环和switch语句是我们最常用的控制流工具,它们让我们能够根据不同的条件执行不同的代码块。本文将深入探讨这些语句的使用方法、技术细节和实际…...
飞书会话消息左右排列
飞书会话消息左右排列 1. 飞书登录后,点击头像,弹出菜单有个按钮设置 2. 3....
.net 支持跨平台(桌面)系列技术汇总
1. 首先微软老大哥的.net core 。 .NET Core 是微软开发的一个跨平台、高性能的开源框架,用于构建云和互联网连接的新型应用。 它允许开发者在 Windows、macOS 和 Linux 上使用喜爱的开发工具进行开发,并支持部署到云或本地环境。 .NET Core 是对 .NET …...
springboot 静态资源访问
最近在学习springboot,在学习中一个静态资源访问,难道了我三天,在网上找了很多的资料,又是配置,又是重写WebMvcConfigurationSupport,因为以前没有接触,本来很简单的事情走了很多弯路࿰…...
【linux学习指南】初识Linux进程信号与使用
文章目录 📝信号快速认识📶⽣活⻆度的信号📶 技术应⽤⻆度的信号🌉 前台进程(键盘)🌉⼀个系统函数 📶信号概念📶查看信号 🌠 信号处理🌉 忽略此信…...
L1G1000 书生大模型全链路开源开放体系笔记
关卡任务 观看本关卡视频后,写一篇关于书生大模型全链路开源开放体系的笔记。 视频链接:【书生浦语大模型全链路开源体系】 : 书生浦语大模型开源开放体系_哔哩哔哩_bilibili 书生大模型全链路开源开放体系笔记 在人工智能领域,大模型的…...
亚信安全与飞书达成深度合作
近日,亚信安全联合飞书举办的“走近先进”系列活动正式走进亚信。活动以“安全护航信息化 共筑数字未来路”为主题,吸引了众多数字化转型前沿企业的近百位领导参会。作为“走近先进”系列的第二场活动,本场活动更加深入挖掘了数字化转型的基础…...
深入讲解Spring Boot和Spring Cloud,外加图书管理系统实战!
很抱歉,我的疏忽,说了这么久还没有给大家详细讲解过Spring Boot和Spring Cloud,那今天给大家详细讲解一下。 大家可以和下面这三篇博客一起看: 1、Spring Boot 和 Spring Cloud 微服务开发实践详解https://blog.csdn.net/speaking_me/artic…...
AI-调查研究-01-正念冥想有用吗?对健康的影响及科学指南
点一下关注吧!!!非常感谢!!持续更新!!! 🚀 AI篇持续更新中!(长期更新) 目前2025年06月05日更新到: AI炼丹日志-28 - Aud…...
以下是对华为 HarmonyOS NETX 5属性动画(ArkTS)文档的结构化整理,通过层级标题、表格和代码块提升可读性:
一、属性动画概述NETX 作用:实现组件通用属性的渐变过渡效果,提升用户体验。支持属性:width、height、backgroundColor、opacity、scale、rotate、translate等。注意事项: 布局类属性(如宽高)变化时&#…...
Java 8 Stream API 入门到实践详解
一、告别 for 循环! 传统痛点: Java 8 之前,集合操作离不开冗长的 for 循环和匿名类。例如,过滤列表中的偶数: List<Integer> list Arrays.asList(1, 2, 3, 4, 5); List<Integer> evens new ArrayList…...
Leetcode 3577. Count the Number of Computer Unlocking Permutations
Leetcode 3577. Count the Number of Computer Unlocking Permutations 1. 解题思路2. 代码实现 题目链接:3577. Count the Number of Computer Unlocking Permutations 1. 解题思路 这一题其实就是一个脑筋急转弯,要想要能够将所有的电脑解锁&#x…...
linux arm系统烧录
1、打开瑞芯微程序 2、按住linux arm 的 recover按键 插入电源 3、当瑞芯微检测到有设备 4、松开recover按键 5、选择升级固件 6、点击固件选择本地刷机的linux arm 镜像 7、点击升级 (忘了有没有这步了 估计有) 刷机程序 和 镜像 就不提供了。要刷的时…...
Cinnamon修改面板小工具图标
Cinnamon开始菜单-CSDN博客 设置模块都是做好的,比GNOME简单得多! 在 applet.js 里增加 const Settings imports.ui.settings;this.settings new Settings.AppletSettings(this, HTYMenusonichy, instance_id); this.settings.bind(menu-icon, menu…...
CocosCreator 之 JavaScript/TypeScript和Java的相互交互
引擎版本: 3.8.1 语言: JavaScript/TypeScript、C、Java 环境:Window 参考:Java原生反射机制 您好,我是鹤九日! 回顾 在上篇文章中:CocosCreator Android项目接入UnityAds 广告SDK。 我们简单讲…...
unix/linux,sudo,其发展历程详细时间线、由来、历史背景
sudo 的诞生和演化,本身就是一部 Unix/Linux 系统管理哲学变迁的微缩史。来,让我们拨开时间的迷雾,一同探寻 sudo 那波澜壮阔(也颇为实用主义)的发展历程。 历史背景:su的时代与困境 ( 20 世纪 70 年代 - 80 年代初) 在 sudo 出现之前,Unix 系统管理员和需要特权操作的…...
WEB3全栈开发——面试专业技能点P2智能合约开发(Solidity)
一、Solidity合约开发 下面是 Solidity 合约开发 的概念、代码示例及讲解,适合用作学习或写简历项目背景说明。 🧠 一、概念简介:Solidity 合约开发 Solidity 是一种专门为 以太坊(Ethereum)平台编写智能合约的高级编…...
深度学习习题2
1.如果增加神经网络的宽度,精确度会增加到一个特定阈值后,便开始降低。造成这一现象的可能原因是什么? A、即使增加卷积核的数量,只有少部分的核会被用作预测 B、当卷积核数量增加时,神经网络的预测能力会降低 C、当卷…...
