io+day5

1,select服务端

1 #include<myhead.h>2 3 #define PORT 8888              //端口号4 #define IP "192.168.228.165"       //IP地址5 6 7 int main(int argc, const char *argv[])8 {9     //1、创建用于接受连接的套接字10     int sfd = socket(AF_INET, SOCK_STREAM, 0);11     if(sfd == -1)12     {                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      13         perror("socket error");14         return -1;15     }16 17     printf("socket success sfd = %d\n", sfd);    //418 19 20     //设置端口号快速重用21     int reuse = 1;22     if(setsockopt(sfd, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(reuse)) == -1)23     {24         perror("setsockopt error");25         return -1;26     }27     printf("设置端口快速重用成功 _%d_ %s_ %s_\n", __LINE__, __FILE__, __func__);28 29 30 31 32 33     //2、绑定IP地址和端口号34     //2.1、填充要绑定的地址信息结构体35     struct sockaddr_in sin;36     sin.sin_family     = AF_INET;         //表明是ipv437     sin.sin_port     = htons(PORT);        //端口号38     sin.sin_addr.s_addr = inet_addr(IP);     //IP地址39 40     //2.2、绑定41     if(bind(sfd, (struct sockaddr*)&sin, sizeof(sin))==-1)42     {43         perror("bind error");44         return -1;45     }46     printf("bind success _%d_ %s_ %s_\n", __LINE__, __FILE__, __func__);47 48     //3、将套接字设置成被动监听状态49     if(listen(sfd, 128) == -1)50     {51         perror("listen error");52         return -1;53     }54 55     printf("listen success _%d_ %s_ %s_\n", __LINE__, __FILE__, __func__);56 57     //4、阻塞等待客户端连接请求,如果有新的客户端连接,则创建一个新的用于通信的套接字58     //4.1、定义客户端地址信息结构体59     struct sockaddr_in cin;             //客户端地址信息结构体60     cin.sin_family     = AF_INET;61     socklen_t socklen = sizeof(cin);          //客户端地址信息的大小62 63 64     定义一个用于检测文件描述符的集合65     fd_set readfds, tempfds;                          //在栈区定义66 67     清空容器中的内容68     FD_ZERO(&readfds);69     将要检测的文件描述符放入集合中70     FD_SET(sfd, &readfds);           //将sfd文件描述符放入71     FD_SET(0, &readfds);             //将0号文件描述符放入72 73 74 75     //定义一个容器76     char buf[128] = "";77     int res = 0;             //接收select的返回值78     int newfd = -1;          //存放用于最新连接客户端的套接字79     int maxfd = sfd;          //定义控制select函数中最大文件描述符80 81     struct sockaddr_in saveCin[1024];       //用于存放客户端地址信息结构体82 83 84     while(1)85     {86         将集合内容复制一份87         tempfds = readfds;88 89         使用select阻塞等待集合中的文件描述符有事件产生90         res = select(maxfd+1, &tempfds, NULL, NULL, NULL);91         if(res == -1)92         {93             perror("select error");94             return -1;95         }else if(res == 0)96         {97             printf("time out\n");98             return -1;99         }
100 
101 
102         //遍历所有集合中文件描述符
103         for(int i=0; i<=maxfd; i++)
104         {
105             //判断当前i是否在集合中,如果不在,直接判断下一个
106             if(!FD_ISSET(i, &tempfds))
107             {
108                 continue;
109             }
110 
111             判断sfd是否还在集合中
112             if( i == sfd)
113             {
114                 //4.2、阻塞接收客户端的链接请求,并且获取客户端的地址信息
115                 newfd = accept(sfd, (struct sockaddr*)&cin, &socklen);
116                 if(newfd == -1)
117                 {
118                     perror("accept error");
119                     return -1;
120                 }
121                 printf("accept success _%d_ %s_ %s_\n", __LINE__, __FILE__, __func__);
122 
123                 将newfd放入readfds中
124                 FD_SET(newfd , &readfds);
125 
126                 //更新maxfd
127                 if(newfd > maxfd)
128                 {
129                     maxfd = newfd;
130                 }
131 
132                 //将最新的客户端套接字放入数组的下标为new的位置
133                 saveCin[newfd] = cin;
134                 printf("newfd = %d\n", newfd);
135 
136             }else if(i == 0 )    //判断是否是终端输入
137 
138             {
139                 char buf1[1000] = "";
140 
141                 bzero(buf, sizeof(buf));
142                 //从终端获取数据
143                 fgets(buf, sizeof(buf), stdin);       //从终端获取数据
144                 buf[strlen(buf)-1]='\0';
145                 printf("触发终端输入事件:%s\n", buf);
146 
147                sprintf(buf1, "%s%s", "系统消息:", buf);
148 
149                 //将数据发送给所有客户端
150                 for(int j=4; j<=maxfd; j++)
151                 {
152                     send(j, buf1,sizeof(buf1), 0);
153                 }
154 
155 
156             }else
157             {
158                 //5、收发数据使用newfd完成通信
159                 char buf[128] = "";
160                 //清空字符串
161                 bzero(buf, sizeof(buf));
162                 int ret = recv(i, buf, sizeof(buf), 0);        //从套接字中读取客户端发来的消息
163 
164                 //判断收到的结果
165                 if(ret == 0)
166                 {
167                     printf("客户端已经下线\n");
168                     close(i);             //关闭通信的套接字
169 
170                     将当前的文件描述符从集合中删除
171                     FD_CLR(i, &readfds);
172 
173                     更新maxfd
174                     for(int j=maxfd; j>=0; j--)
175                     {
176                         //判断当前的j是否在集合中,如果在,则为maxfd
177                         if(FD_ISSET(j, &readfds))
178                         {
179                             maxfd = j;
180                             break;
181                         }
182                     }
183 
184                     continue;           //继续判断下一个
185                 }else if(ret < 0)
186                 {
187                     perror("recv error");
188                     return -1;
189                 }
190 
191                 printf("[%s:%d]:%s\n", inet_ntoa(saveCin[i].sin_addr), ntohs(saveCin[i].sin_port), buf);
192 
193                 //将读取的信息,加上一些字符发送回去
194                 strcat(buf, "*_*");
195                 send(i, buf, sizeof(buf), 0);
196 
197 
198             }
199         }
200 
201     }
202 
203 
204 
205     //6、关闭所有套接字
206     close(sfd);               //关闭监听
207 
208     return 0;
209 }
~                                                                                                                          
 #include <myhead.h>2 3 #define SERPORT 8888              //服务器端口号4 #define SERIP "192.168.228.165"       //服务器IP地址5 6 int main(int argc, const char *argv[])7 {8     //创建用于通信的套接字9     int cfd = socket(AF_INET,SOCK_STREAM,0);10     if(cfd == -1)11     {12         perror("socket error");13         return -1;14     }15 16     //连接服务器17     ///填充服务器地址信息结构体18     struct sockaddr_in sin;19     sin.sin_family = AF_INET;20     sin.sin_port = htons(SERPORT);21     sin.sin_addr.s_addr = inet_addr(SERIP);22 23     ///连接服务器24     if(connect(cfd,(struct sockaddr *)&sin,sizeof(sin)) == -1)25     {26         perror("connect error");27         return -1;28     }29 30     //创建用于检测文件描述符的集合31     fd_set readfds,tempfds;32 33     //清空集合34     FD_ZERO(&readfds);35 36     //将要检测的文件描述符放入集合中37     FD_SET(cfd,&readfds);38     FD_SET(0,&readfds);39 40     int res = 0;    //接收select的返回值41     int maxfd = cfd;  //集合中值最大的文件描述符42 43     //向服务器进行数据的收发44     char buf[128] = "";45     int ret = 0;    //接收recv的返回值46     while(1)47     {48         tempfds = readfds;                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            49 50         res = select(maxfd+1,&tempfds,NULL,NULL,NULL);51         if(res == -1)52         {53             perror("select error");54             return -1;55         }else if(res == 0)56         {57             printf("time out\n");58             return -1;59         }60 61         //遍历集合中所有的文件描述符62         for(int i = 0;i <= maxfd;i++)63         {64             //判断当前文件描述符是否在集合中65             if(!FD_ISSET(i,&readfds))66             {67                 continue;68             }69 70 71             //判断0号文件描述符是否还在集合中72             if(0 == i)73             {74                 //从标准输入中读取数据75                 fgets(buf,sizeof(buf),stdin);76                 buf[strlen(buf)-1] == 0;77 78                 //将数据发送到服务器79                 if(send(cfd,buf,sizeof(buf),0) == -1)80                 {81                     perror("send error");82                     return -1;83                 }84 85             }else if(cfd == i)     //判断cfd是否还在集合中86             {87                 //接收来自服务器的消息88                 ret = recv(cfd,buf,sizeof(buf),0);89                 if(ret == -1)90                 {91                     perror("recv error");92                     return -1;93                 }else if(ret == 0)94                 {95                     printf("服务器已关闭\n");96                     return -1;97                 }98 99                 printf("服务器消息:%s\n",buf);
100             }
101         }
102     }
103 
104     //关闭文件描述符
105     close(cfd);
106 
107     return 0;
108 }

效果图

poll客户端

  1 #include <myhead.h>2 3 #define IP "192.168.228.165"4 #define PORT 88885 6 int main(int argc, const char *argv[])7 {8     //创建用于连接的套接字9     int sfd = socket(AF_INET,SOCK_STREAM,0);10     if(sfd == -1)11     {12         perror("socket error");13         return -1;14     }15 16     //绑定服务器IP和端口号17     ///填充服务器地址信息结构体18     struct sockaddr_in sin;19     sin.sin_family = AF_INET;20     sin.sin_port = htons(PORT);21     sin.sin_addr.s_addr = inet_addr(IP);22 23     ///绑定24     if(bind(sfd,(struct sockaddr *)&sin,sizeof(sin)) == -1)25     {26         perror("bind error");27         return -1;28     }29     printf("bind success\n");30 31     //将连接用套接字设置为被动监听状态32     if(listen(sfd,128) == -1)33     {                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              34         perror("listen error");35         return -1;36     }37     printf("listen success\n");38 39     //定义一个集合管理sfd和打开的通信用文件描述符40     struct pollfd fds[1024];41     int maxfd = 0;42 43 44     //手动放入sfd45     fds[0].fd = sfd;46     fds[0].events = POLLIN;     //表明为读事件47 48     //将fds中其余元素初始化为-149     for(int i = 4;i <= 1024;i++)50     {51         fds[i].fd = -1;52     }53 54     //填充客户端地址信息结构体55     struct sockaddr_in cin;56     cin.sin_family = AF_INET;57     socklen_t socklen = sizeof(cin);58 59 60     char cbuf[128] = "";  //给客户端用的容器61     int nfd;62     int res = 0;  //接收poll返回的结果63     while(1)64     {65         res = poll(fds,maxfd+1,-1);66         if(res == -1)67         {68             perror("select");69             return -1;70         }71         else if(res == 0)72         {73             continue;;74         }75         else if(res > 0)                //说明检测到了有文件描述符对应的缓冲区的数据发生了改变76         {77             if(fds[0].revents ==  POLLIN)    //表明有新的客户连接进来了78             {79                 int nfd = accept(sfd,(struct sockaddr*)&cin,&socklen);  //阻塞在此处,直到有客户端连接上来80                 if(nfd == -1)   //增加这些错误的判断非常重要,可以帮助找到出现问题的地方81                 {82                     perror("accept");83                     return -1;84                 }85 86                 //将新的文件描述符加入到集合中87                 for(int i = 1;i < 1024;i++)88                 {89                     if( fds[i].fd == -1)90                     {91                         fds[i].fd = nfd;92                         fds[i].events = POLLIN;93                         break;94                     }95                 }96 97                 //更新最大的文件描述符98                 if(nfd > maxfd)99                 {
100                     maxfd = nfd;
101                 }
102             }
103 
104             for(int i = 1;i <= maxfd;i++)     //轮询客户端对应的文件描述符
105             {
106                 if(fds[i].revents == POLLIN)  //说明此文件描述符对应的客户端发送来了数据
107                 {
108                     int ret = read(fds[i].fd,cbuf,sizeof(cbuf));
109                     if(ret == -1)
110                     {
111                         perror("read");
112                         exit(-1);
113                     }
114                     else if(ret == 0)
115                     {
116                         printf("client closed\n");
117                         close(fds[i].fd);   //关闭对应的文件描述符
118                         fds[i].fd = -1;   //在fds中清空对应的文件描述符
119                     }
120                     else if(ret > 0)
121                     {
122                         printf("read buf = %s\n",cbuf);
123                         write(fds[i].fd,cbuf,strlen(cbuf)+1);
124                     }
125 
126 
127                 }
128             }
129         }
130     }
131     //关闭所有套接字
132     close(sfd);
133 
134     return 0;
135 
1 #include<myhead.h>2 #define SERIP "192.168.228.165"3 #define SERPORT 88884 #define CLIIP "192.168.228.165"5 #define CLIPORT 66666 7 int main(int argc, const char *argv[])8 {9     //1、创建客户端用于通信的套接字10     int cfd = socket(AF_INET, SOCK_STREAM, 0);11     if(cfd == -1)12     {13         perror("socket error");14         return -1;15     }16     printf("cfd = %d\n", cfd);                //317 18 19     //2、绑定(可选)20     //2.1、填充地址信息结构体21     struct sockaddr_in cin;22     cin.sin_family     = AF_INET;            //使用的是ipv4通信23     cin.sin_port     = htons(CLIPORT);       //服务器端口号24     cin.sin_addr.s_addr     = inet_addr(CLIIP);       //服务器IP地址25     //2.2、绑定工作26     if(bind(cfd, (struct sockaddr*)&cin, sizeof(cin)) == -1)27     {28         perror("bind error");29         return -1;30     }31     printf("bind success\n");32 33 34     //3、连接服务器35     //3.1、填充服务器地址信息结构体36     struct sockaddr_in sin;37     sin.sin_family     = AF_INET;            //使用的是ipv4通信38     sin.sin_port     = htons(SERPORT);       //服务器端口号39     sin.sin_addr.s_addr     = inet_addr(SERIP);       //服务器IP地址                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                40 41     //3.2、连接服务器42     if(connect(cfd, (struct sockaddr*)&sin, sizeof(sin)) ==-1)43     {44         perror("connect error");45         return -1;46     }47     printf("connect success\n");48 49     //4、收发数据(send、recv、read、write)50     char buf[128] = "";51     char rbuf[128] = "";52 53     定义一个集合管理0号文件描述符和cfd54     struct pollfd fds[2];55 56     //将0号文件描述符放入57     fds[0].fd = 0;58     fds[0].events = POLLIN;          //表明要进行读事件59 60     //将cfd放入集合61     fds[1].fd = cfd;62     fds[1].events = POLLIN;63 64     int res = 0;     //接收poll返回的结果65 66 67     while(1)68     {69         res = poll(fds, 2, -1);          //第三个参数如果是负数,表明一直等待70         if(res == -1)71         {72             perror("poll error");73             return -1;74         }else if(res == 0)75         {76             printf("time out\n");77             return -1;78         }79 80 81         bzero(buf, sizeof(buf));82         bzero(rbuf, sizeof(rbuf));83 84 85 86         //判断是否是发送数据满足条件87         if(fds[0].revents == POLLIN)88         {89             fgets(buf, sizeof(buf), stdin);       //从标准输入中读取数据90             buf[strlen(buf)-1] = '\0';91 92             //将数据发送给服务器93             send(cfd, buf, sizeof(buf), 0);94 95             //如果输入的是quit则退出96             if(strcmp(buf,"quit") == 0)97             {98                 break;99             }
100         }
101 
102 
103 
104         //判断是否为接收数据满足条件
105         if(fds[1].revents == POLLIN)
106         {
107 
108             //接收服务器发送来的消息
109             int res = recv(cfd, rbuf, sizeof(rbuf), 0);
110             if(res == 0)
111             {
112                 printf("服务器已经关闭\n");
113                 break;
114             }
115             printf("rbuf = %s\n", rbuf);
116         }
117 
118     }
119 
120     //5、关闭客户端套接字
121     close(cfd);
122 
123 
124     return 0;
125 }
126 
~                                                                                

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/160893.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

pikachu靶场PHP反序列化漏洞

pikachu靶场PHP反序列化漏洞 源码分析 查看源代码 class S{var $test "pikachu";function __construct(){echo $this->test;} }// O:1:"S":1:{s:4:"test";s:29:"<script>alert(xss)</script>";} $html; if(isset($_PO…

unityplayer.dll如何安装?unityplayer.dll缺失的解决方法

Unityplayer.dll是Unity引擎所需的一个重要动态链接库&#xff08;DLL&#xff09;文件&#xff0c;负责在运行Unity创建的游戏或应用程序时处理相关的软件逻辑。如果此文件意外丢失&#xff0c;可能会导致错误提示&#xff0c;甚至阻止程序的正常运行。因此&#xff0c;对于许…

Threejs_12 物体阴影的实现

所以在Threejs的画布世界之中&#xff0c;一个物体有自己的影子呢&#xff1f; 阴影效果的实现 你需要先知道在threejs世界中&#xff0c;有哪些灯光或者材质是可以产生阴影效果的 环境光没有阴影 平行光有阴影(太阳) 点光源有阴影(灯泡) 聚光灯有阴影(手电筒) 平面光源没有…

代码随想录二刷 | 链表 |环形链表II

代码随想录二刷 &#xff5c; 链表 &#xff5c;环形链表II 题目描述解题思路 & 代码实现判断链表是否有环如何找到环的入口 题目描述 142.环形链表II 给定一个链表的头节点 head &#xff0c;返回链表开始入环的第一个节点。 如果链表无环&#xff0c;则返回 null。 如…

图神经网络:消息传递算法

一、说明 图网络-GNN&#xff08;Graph Neural Networks&#xff09;是近几年研究的主题之一&#xff0c;虽不及深度神经网络那么火爆&#xff0c;但在一些领域&#xff0c;如分子化学方面是不得不依赖的理论。本文就一些典型意义的图神经网络消息传递展开阐述。 二、图网络简述…

Vue 3 渲染机制解密:从模板到页面的魔法

Vue 3 渲染机制解密 前言Vue 3的响应性系统1. **Reactivity API:**2. **Proxy 对象:**3. **Getter 和 Setter:**4. **依赖追踪:**5. **批量更新:**6. **异步更新:**7. **递归追踪:**8. **删除属性:** 虚拟DOM的角色1. **减少直接操作真实 DOM:**2. **高效的批量更新:**3. **跨平…

【java】想要限制每次查询的结果集不能超过10000行,该如何实现?

文章目录 前言 前言 对于一些Saas化软件&#xff0c;当某个租户在执行查询SQL时&#xff0c;如果查询条件出现了BUG&#xff0c;导致去查了所有租户的数据&#xff0c;这种情况是非常严重的&#xff0c;此时就需要在架构层面做限制&#xff0c;禁止一些特殊SQL的执行&#xff…

@PropertySource适配通配符加载到Environment的一种方案

PropertySource可将配置文件加载到内存&#xff0c;时间有限说干的&#xff0c;PropertySource注解有4个参数&#xff0c;其中value表示要加载文件的路径&#xff0c;这个参数不支持通配符。还有一个参数PropertySourceFactory是加载配置文件的工厂&#xff0c;这两个参数配合使…

【GUI】-- 13 贪吃蛇小游戏之食物及成绩判断

GUI编程 04 贪吃蛇小游戏 4.4 第四步&#xff1a;食物及成绩判断 首先&#xff0c;添加食物与分数的数据定义&#xff1a; //食物的坐标int foodX;int foodY;Random random new Random();//积分面板数据结构int score;在初始化方法中&#xff0c;添加(画出)食物与分数&…

CSDN最新最全pytest系列——pytest-base-url插件之配置可选的项目系统UR

前言 ①当我们的自动化代码完成之后&#xff0c;通常期望可以在不同的环境进行测试&#xff0c;此时可以将项目系统的URL单独拿出来&#xff0c;并且可以通过pytest.ini配置文件和支持pytest命令行方式执行。 ② pytest-base-url 是一个简单的pytest插件&#xff0c;它通过命…

纽扣电池上架TEMU、亚马逊美国站需要做什么认证?纽扣电池认证标准16CFR1700.15,16CFR1700.20

近日&#xff0c;Temu连发多条卖家弹窗内容均为商品质量事故违规处理通告。其中一条为卖家销售的车载吸尘器发生烧毁、冒烟等情况&#xff0c;产生用户人伤、财损等舆情。经查实是商家偷换关键部件锂电池&#xff0c;导致商品质量下降造成事故。TEMU对于问题车载吸尘器处理结果…

设计循环队列,解决假溢出问题

什么是假溢出&#xff1f; 当我们使用队列这种基本的数据结构时&#xff0c;很容易发现&#xff0c;随着入队和出队操作的不断进行&#xff0c;队列的数据区域不断地偏向队尾方向移动。当我们的队尾指针指向了队列之外的区域时&#xff0c;我们就不能再进行入队操作了&#xff…

单链表在线OJ题二(详解+图解)

1.在一个排序的链表中&#xff0c;存在重复的结点&#xff0c;请删除该链表中重复的结点&#xff0c;重复的结点不保留&#xff0c;返回链表头指针 本题的意思是要删除链表中重复出现的节点&#xff0c;然后返回删除重复节点后的链表。 我们可以直接用一个哨兵位以便于观察链表…

指针变量和地址

A.指针变量和地址 理解了内存和地址的关系&#xff0c;我们再回到C语⾔&#xff0c;在C语⾔中创建变量其实就是向内存申请空间&#xff0c;比如&#xff1a; #include <stdio.h> int main() {int a 10;return 0; } ⽐如&#xff0c;上述的代码就是创建了整型变量a&…

spring-boot-admin-starter-server监控springboot项目

文章目录 场景实现具体操作展示 场景 监控三件套Prometheus、Grafana、Alertmanager 部署起来太复杂,如果公司没有运维而且项目很小就可以使用spring-boot-admin-starter-server替代。这个包使用起来还是很简单的, 下面就实现一个对springCloud项目的监控 实现 参考 项目 具体操…

经典中的经典之字符串

前言&#xff1a;前段时间发烧了&#xff0c;所以耽误了很多事情&#xff0c;一直没有更新&#xff0c;多穿点衣服&#xff0c;感冒不好受。 接下来有时间就会陆续更新一些基础的算法题&#xff0c;题目都很经典&#xff0c;大家可以先尝试着做&#xff0c;再看 解析。 第一…

Windows常用cmd网络命令详解

中午好&#xff0c;我的网工朋友。 上回给你们梳理了一些有趣的cmd命令&#xff0c;很多朋友希望再拓展一下&#xff0c;这不就来了&#xff1f; 今天从windows切入&#xff0c;给你分享一些常用cmd网络命令&#xff0c;如果能熟悉上手&#xff0c;很多功能都可以快速实现&am…

Java Class 类文件格式看这一篇就够了

本文将揭开Java Class文件的神秘面纱&#xff0c;带你了解Class文件的内部结构&#xff0c;并从Class文件结构的视角告诉你&#xff1a; 为什么Java Class字节码文件可以“写一次&#xff0c;遍地跑”&#xff1f;为什么常量池的计数从1开始&#xff0c;而不是和java等绝大多数…

【JVM精讲与GC调优教程(概述)】

如何理解虚拟机(JVM)跨语言的平台 java虚拟机根本不关心运行在其内部的程序到底是使用何种编程语言编写的,他只关心“字节码”文件。 java不是最强大的语言,但是JVN是最强大的虚拟机。 不存在内存溢出? 内存泄露? JAVA = (C++)–; 垃圾回收机制为我们打理了很多繁琐的…

【人工智能入门学习资料福利】

总目录如下&#xff08;部分截取&#xff09;&#xff1a; 百度网盘链接&#xff1a;https://pan.baidu.com/s/1bfDVG-xcPR3f3nfBJXxqQQ?pwdifu6 提取码&#xff1a; ifu6