poll
历史地位:跨平台不如select,性能不如epoll,比较尴尬的地位
- 作用:IO多路转接能够同时等待多个文件描述符的就绪状态,换句话说,可以帮助我们同时监控多个文件描述符
接口
int poll(struct pollfd *fds,nfds_t nfds,int timeout);
- fds:事件结构数组,存放监控文件的文件描述符,关心的事件,真实产生的事件
- nfds:描述fds数组当中有多少有效元素
- timeout:超时时间,单位s;>0:表示带有超时时间的等待;==0:非阻塞,需要搭配循环使用
- 返回值:>0:表示多少文件描述符就绪;==0:监控超时;<0:监控出错(例如无效的文件描述符)
事件结构
struct pollfd{
int fd;//要监控的文件描述符
stort event;//关心文件描述符产生的事件:PLOOIN:可读事件,POLLOUT:可写事件;监控多个事件时,用按位或的方式
stort revent;//文件描述符真实产生的事件
}
struct pollfd arr;
arr.fd=0;
arr.event=POLLIN;
优缺点
- 优点
1.提出了事件结构的方式,在给poll函数传递参数的时候,不需要分别添加到“事件集合”当中
2.事件结构数组的大小可以更新程序员自己进行定义,并没有要求上限
3.不用在监控就绪之后,重新添加文件描述符
- 缺点
1.不支持跨平台
2.内核也是对事件结构数组监控的时候采用轮询遍历的方式
epoll
历史地位:迄今为止,linux平台性能最好的IO多路转接模型,没有之一
接口
int epoll_create(int size);
size:目前没有含义,但是要大于0,兼容旧内核
int epoll_ctl(int epfd,int op,int fd,struct epoll_event *event);
- epfd:epoll操作句柄
- op:
EPOLL_CTL_ADD:添加一个文件描述符到对应的时机结构epoll当中
EPOLL_CTL_MOD:修改一个文件描述符的事件结构
EPOLL_CTL_DEL:从epoll当中删除一个文件描述符对应的事件结构 - fd:待处理(添加,修改,删除)的文件描述符
- event:文件描述符对应的事件结构
struct epoll_event{
unit32_t event;
EPOLLIN:可读事件
EPOLLOUT:可写事件
epoll_data_t data;
}
int epoll_wait(int epfd,struct epoll_event *event,int maxevent,int timeout);
- epfd :epoll操作句柄
- event:事件结构数组,从epoll中获取就绪的事件结构
- maxevent:最多一次获取多少个事件结构
- timeout:>0:带有超时时间 ;==0:非阻塞;<0:阻塞
- 返回值:返回就绪文件描述符的个数
epoll_creat创建的数据结构中用红黑树来监控文件描述符,查询效率lgn,就绪后放入双向链表当中
epoll_wait每次从双向链表中获取就绪的事件结构
epoll的工作模式
- LT(默认):水平触发:当读就绪或者写就绪的时候,则一定乐此不疲的通知(对程序员而言友好)
- ET:边缘触发:当读就绪或者写就绪的时候,只会通知 一次(要求程序员一次将数据全部读回来)