(推荐!)三张图彻底搞懂select函数

欢迎交流 QQ 2431173627 微信 ccc17862701790

 存在问题

设计思路

工作过程 

第一步

第二步

​第三步

 

特点分析

 程序实例


 存在问题



用socket基本的一套api已经可以构建一个简单的tcp服务器了

思路就是 加一个while循环 在循环里面服务器程序用socket bind listen accept recv send 一条龙

具体可以看我写的这一篇博客 socket网络编程基础篇-------如何写一个简单的TCP服务器

但是这样简单的tcp服务器在只有单个客户端请求的时候是可以应付的,但是在有多个客户端请求的时候是存在很大问题的

以下面的场景作为例子

 

----->进入while循环

--->服务器用socket创建监听套接字(比如该套接字的文件描述符号为4)

-->调用listen函数监听该套接字

-->新来一个客户端调用connect请求连接

--->服务器调用accpet函数接受客户端请求并创建了针对这个客户端的数据传输套接字(比如文件描述符号为5) 

--->在这个套接字5上调用read函数读客户端发过来的数据

-->新来一个客户端调用connect请求连接

--->服务器调用accpet函数接受客户端请求并创建了针对这个客户端的数据传输套接字(比如文件描述符号为6) 

--->在这个套接字6上调用read函数读客户端发过来的数据

-->新来一个客户端调用connect请求连接

--->服务器调用accpet函数接受客户端请求并创建了针对这个客户端的数据传输套接字(比如文件描述符号为7) 

--->在这个套接字7上调用read函数读客户端发过来的数据

........(上述过程在服务器端用while循环 多个客户端请求的时候就不断延续上述过程) 

 

 

 上述的这样一个过程存在一个严重的问题 在多个客户端有连接请求或者读写请求的时候

当使用accpet函数的时候发现没有客户端连接时会阻塞,
同样当使用read/write函数的时候发现客户端没有数据传过来时也会阻塞
所以在上述多个客户端请求的过程中,

(1)假如在某个循环中调用read函数阻塞了,这个时候假如又来了一个客户端连接 
由于现在服务器端程序卡在了read这里
 就没办法进入下一次循环到accept那里 ,这样的环这个想建立连接的客户端就一直阻塞在那里

(2)假如在某一个循环调用accept阻塞了,服务端程序由于卡在accept这里不能往下执行到read函数 
故也响应不了前面已经建立连接的客户端套接字发过来的数据,这样根本就不能处理多个客户端的服务请求,
导致客户端的请求大大延迟


那怎么办呢?所以就引入了多路io复用,
他有三种实现机制----select函数,poll函数,epoll函数 这里先介绍select

设计思路


对于select函数工作过程的理解
select函数是怎么工作的呢?我是这么理解的
上面这个服务器客户端交互过程本质上是文件io函数(accept/read)对文件描述符(4,5,6,7)的操作过程.
出现问题的罪魁祸首就是,
accep/read函数"自作主张"就直接去连接/读取文件描述符对应的套接字,
丝毫不管对应文件描述符的套接字是否可以连接/读取
万一对应文件描述符的套接字没有连接/数据请求传输过来,这两个函数自然就会阻塞.


理想的情况应该是请一个"监控员" ,
在执行read/accept之前 先让这个监管员依次检查一番
看哪个文件描述符有连接过来了或者有数据传输过来了 
这时候再调用accept/read函数就不会阻塞了
如果监管员这一轮查找 没看到哪个文件描述符有连接过来了或者有数据传输过来了 
就在进入下一轮的检查 就不调用accept或者read
虽然在这个监管员工作也会耽搁一定的时间(select每次检查都是阻塞查询) 但是比起accept/read函数盲目的就上来读写一个文件描述符 然后卡在那大半天  效率明显来的高 
select就起了这样一个"监管员"的作用,


工作过程 


三步走!

  • 4
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值