I/O多路复用

定义:
I/O多路复用是一种同步IO模型,实现一个线程可以监视多个文件句柄;
一旦某个文件句柄就绪,就能够通知应用程序进行相应的读写操作;
没有文件句柄就绪时会阻塞应用程序,交出cpu。
其实简单的理解就是使用单个线程通过记录跟踪每一个流(I/O)的状态来同时管理多个I/O,以此来减少线程的创建和切换的开销,进而提高服务器的吞吐能力。

  • 多路是指网络连接
  • 复用是指同一个线程(使用一个线程处理 N 个 IO 请求,没有上下文切换和线程的创建和销毁,程序更快)
  • 有三种实现方式

1、select

(1) 工作原理

内核调用select传入要监听的文件描述符集合(可读、可写或异常)开始监听,select处于阻塞状态,当有事件发生或设置的等待时间timeout到了就会返回,返回时传出有事件发生的文件描述符集合。但select传出的集合并没有告诉用户集合中包括哪几个就绪的文件描述符,需要用户后续进行遍历操作。

(2) select底层采用数组存储

(3) 优点:

  • select的可移植性较好,可以跨平台;
  • select可设置的监听时间timeout精度更好,可精确到微秒,而poll为毫秒。

(4) 缺点

  • select支持的文件描述符数量上限为1024,不能根据用户需求进行更改(除非修改内核相关代码);
  • select每次调用时都要将文件描述符集合从用户态拷贝到内核态,开销较大;
  • select返回的就绪文件描述符集合,需要用户遍历监听的所有文件描述符是否在该集合中,当监听描述符数量很大时效率较低。

2、poll(轮询机制)

(1)poll工作原理

内核调用poll传入要监听的文件描述符数组开始监听,poll处于阻塞状态,当有事件发生或设置的等待时间timeout到了就会返回,返回之前将数组中有事件发生的文件描述符所在的pollfd中的revents设置为返回事件的标志符,返回时传出更新后的数组。与select一样,poll传出的数组也没有告诉用户哪几个文件描述符发生了事件,需要用户遍历查询。返回值小于0,时,表示出错;返回值等于0时,表示poll函数等待超时;返回值大于0时,表示就绪的文件描述符的个数

(2) poll底层采用链表进行存储

(3) 优点

  • poll在文件描述符数量较大时速度比select更快;
  • poll没有文件描述符连接数限制,可根据用户需求设置最大文件数;

(4) 缺点

  • 存储文件描述符的链表不会保存在内核中,poll每次调用时都要将链表从用户空间拷贝到内核空间,开销较大;
  • poll需要用户遍历监控的所有文件描述符的数组查看是否发生事件,当监听描述符数量很大时效率较低;
  • poll的工作模式为水平触发(LT),不支持边沿触发(ET),效率较低。

(5) 操作系统中

  • 不同与select使用三个位图来表示三个fdset的方式,poll使用一个 pollfd的指针实现。
  • poll与select相比,只是没有fd的限制,其它基本一样

(6) 网络中

  • 定义:服务器定时发出询问每一个客户端是否需要其服务,有即给于服务,服务结束后再询问下一个客户端
  • 机制:解决服务器压力过大的问题;轮询应该写在接口里面;列表接口发送请求,返回任务id,根据任务id发送轮询接口请求。
  • 更好的解决方案:HTML5定义了WebSocket协议

3、epoll

(1) epoll工作原理

  • 内核利用epoll_create创建一个epfd文件描述符,并利用红黑树数据结构将其存储到根结点上;
  • 再用epoll_ctl从红黑树中添加、修改或移除文件描述符;
  • 最后内核调用epoll_wait函数开始监听,epoll处于阻塞状态,当有事件发生或设置的等待时间timeout到了就会返回,返回时传出有事件发生文件描述符的结构体数组。
  • 与select、poll不一样的是,epoll直接传出有事件发生的文件描述符数组,不用遍历查询。

(2) epoll底层采用红黑树进行存储

(3) 优点

  • epoll在epoll_wait函数返回时直接传出有事件发生文件描述符的数组,无需遍历查询,效率很高,不会随着文件描述符数量的增加而降低效率;
  • epoll由一组函数实现,epoll_create创建的红黑树保存在内核中,epoll_ctl只需从红黑树中添加、删除或修改节点,无需重复将已有的文件描述符拷贝到内核态中,开销较小;
  • epoll没有文件描述符连接数限制,只跟系统内存的大小有关;
  • epoll支持边沿触发,可减少epoll_wait调用次数,提高效率;

(4) 缺点

  • epoll的可移植性没有select好,只能工作在Linux环境下;

(5)epoll vs. select、poll

  • 相对于select和poll来说,epoll更加灵活,没有描述符限制。
  • epoll使用一个文件描述符管理多个描述符,将用户关系的文件描述符的事件存放到内核的一个事件表中,这样在用户空间和内核空间的copy只需一次。

(6) epoll对文件描述符的操作有两种模式

  • LT(level trigger)模式,默认模式
  • 当epoll_wait检测到描述符事件发生并将此事件通知应用程序,应用程序可以不立即处理该事件
  • 下次调用epoll_wait时,会再次响应应用程序并通知此事件。
  • ET(edge trigger)
  • 当epoll_wait检测到描述符事件发生并将此事件通知应用程序,应用程序必须立即处理该事件
  • 如果不处理,下次调用epoll_wait时,不会再次响应应用程序并通知此事件。

4、总结

IO多路复用机制 redis io多路复用的通俗理解_IO多路复用机制 redis