NIO 之 Selector实现原理
NIO 之 Channel实现原理
NIO 之 ByteBuffer实现原理服务器
全部的读写IO都是阻塞操做。网络
select/poll
从程序的角度解释:
将 channel 注册到 seletor 上,经过轮询channel是否就绪,将就绪的channel返回。多线程
epoll
将 channel 注册到 selector 上,基于回调的方式(相似监听者模式),告知selector哪些 channel 已经就绪,而后将就绪的 channel 返回。异步
对比 select/poll 和 epoll 咱们发现epoll效率更高。
若是 select/poll 中注册了大量的 channel,就要不停的轮询每一个channel,来判断那些channel已经就绪。而 epoll 则不须要轮询。性能
jdk1.4 是使用的 select/poll 模型
jdk1.5 之后把select/poll 改成了epoll模型spa
只须要通知内核要执行什么操做,内核执行完成后通知你已经执行完成。.net
下面分析下 阻塞I/O、NIO、AIO的数据处理流程线程
从程序调用Socket.getInputStream()方法开始一直阻塞到程序有可读数据。
阻塞期间程序不能作任何操做。因为网络的传输效率问题,程序基本上都是在等待网络数据传输,所以 阻塞I/O 效率很低。blog
若是客户端有多个用户同时访问服务器,咱们通常会开启多线程进行处理,客户端的请求。以下图:get
客户端请求和服务器线程是一对一进行处理的,大量用户同时访问会形成服务器上建立大量的线程(线程上下文切换问题),可能致使服务器崩溃。
通常咱们会采用线程池进行处理请求。
程序须要调用Seletor.select()方法,阻塞获取就绪的channel。而后从channel中读取数据作响应的处理。这样一个线程就能够处理多个请求,程序只须要处理已经就绪的channel就ok了。
程序调用AIO的accept方法并传入Completionhandler,该方法是非阻塞方法。
等数据准备完成后回调Completionhandler处理响应操做。
程序只须要把具体的操做告知AIO就能够了,具体操做AIO来帮助你来操做。
AIO在性能上相对于NIO没有本质的提高。 AIO只是帮助你从内核中将数据复制到用户空间中,并调用你传入的回调方法。 NIO 是须要程序本身从内核中将数据复制到用户空间中,并须要程序本身调用相应的处理逻辑。