目录
BIO模型
同步阻塞IO
BIO是blocking I/O的简称,它是同步阻塞型IO,其相关的类和接口在java.io下
BIO模型简单来讲,就是服务端为每一个请求都分配一个线程进行处理,I/O操作都是基于流Stream的操作
线程开销:客户端的并发数与后端的线程数成1:1的比例,线程的创建、销毁是非常消耗系统资源的,随着并发量增大,服务端性能将显著下降,甚至会发生线程堆栈溢出等错误
线程阻塞:当连接创建后,如果该线程没有操作时,会进行阻塞操作,这样极大的浪费了服务器资源
NIO模型
同步非阻塞 IO
NIO,称之为New IO 或是 non-block IO (非阻塞IO),这两种说法都可以,其实称之为非阻塞IO更恰当一些
NIO的三大核心组件:Buffer(缓冲区)、Channel(通道)、Selector(选择器/多路复用器)
Buffer(缓冲区):Buffer是一个对象,包含一些要写入或者读出的数据,体现了与原I/O的一个重要区别,在面向流的I/O中,数据读写是直接进入到Steam中,而在NIO中,所有数据都是用缓冲区处理的,读数据直接从缓冲
区读,写数据直接写入到缓冲区。
缓冲区的本质是一个数组,通常是一个字节数组(ByteBuffer),也可以使用其他类型,但缓冲区又不仅仅是一个数组,它还提供了对数据结构化访问以及维护读写位置等操作。
Channel(通道):Channel 是一个通道,管道,网络数据通过Channel读取和写入,Channel和流Stream的不同之处在于Channel是双向的,流只在一个方向上移动(InputStream/OutputStream),而Channel可以用于读写同时进行,即Channel是全双工的。
Selector(选择器/多路复用器):Selector会不断轮询注册在其上的Channel,如果某个Channel上面发生读或者写事件,即该Channel处于就绪状态,它就会被Selector轮询出来,然后通过selectedKeys可以获取就绪Channel的集合,进行后续的I/O操作
AIO模型
异步非阻塞IO
在NIO中,Selector多路复用器在做轮询时,如果没有事件发生,也会进行阻塞
AIO是asynchronous I/O的简称,是异步IO,该异步IO是需要依赖于操作系统底层的异步IO实现。
AIO的基本流程:用户线程通过系统调用,告知kernel内核启动某个IO操作,用户线程返回。kernel内核在整个IO
操作(包括数据准备、数据复制)完成后,通知用户程序,用户执行后续的业务操作。
1.windows下实现成熟,但很少作为百万级以上或者说高并发应用的服务器操作系统来使用。
2.Linux 系统下,异步IO模型在2.6版本才引入,目前并不完善。所以 Linux 下,实现高并发网络编程时都是以
NIO多路复用模型模式为主。
Reactor模型
Reactor线程模型不是Java专属,也不是Netty专属,它其实是一种并发编程模型,是一种思想,具有指导意义。
Reactor模型中定义了三种角色:
Reactor:负责监听和分配事件,将I/O事件分派给对应的Handler。新的事件包含连接建立就绪、读就绪、写就绪等。
Acceptor:处理客户端新连接,并分派请求到处理器链中。
Handler:将自身与事件绑定,执行非阻塞读/写任务,完成channel的读入,完成处理业务逻辑后,负责将结果写出channel。
NIO下单Reactor-单线程
所有的接收连接,处理数据的相关操作都在一个线程中来完成,性能上有瓶颈。
NIO下单Reactor-多线程
把比较耗时的数据的编解码运算操作放入线程池中来执行,提升了性能但还不是最好的方式。
主从Reactor-多线程
主从多线程,对于服务器来说,接收客户端的连接是比较重要的,因此将这部分操作单独用线程去操作
主从Reactor工作模式
这种模式的基本工作流程为:
1.Reactor 主线程 MainReactor 对象通过 select 监听客户端连接事件,收到事件后,通过 Acceptor 处理客
户端连接事件。
2.当 Acceptor 处理完客户端连接事件之后(与客户端建立好 Socket 连接),MainReactor 将连接分配给
SubReactor。(即:MainReactor 只负责监听客户端连接请求,和客户端建立连接之后将连接交由
SubReactor 监听后面的 IO 事件。)
3.SubReactor 将连接加入到自己的连接队列进行监听,并创建 Handler 对各种事件进行处理。
4.当连接上有新事件发生的时候,SubReactor 就会调用对应的 Handler 处理。
5.Handler 通过 read 从连接上读取请求数据,将请求数据分发给 Worker 线程池进行业务处理。
6.Worker 线程池会分配独立线程来完成真正的业务处理,并将处理结果返回给 Handler。Handler 通过
send 向客户端发送响应数据。
7.一个 MainReactor 可以对应多个 SubReactor。
主从Reactor优势
1.MainReactor 线程与 SubReactor 线程的数据交互简单职责明确,MainReactor 线程只需要接收新连接, SubReactor 线程完成后续的业务处理。
2.MainReactor 线程与 SubReactor 线程的数据交互简单, MainReactor 线程只需要把新连接传给SubReactor 线程,SubReactor 线程无需返回数据。
3.多个 SubReactor 线程能够应对更高的并发请求。
这种模式的缺点是编程复杂度较高。但是由于其优点明显,在许多项目中被广泛使用,包括 Nginx、Memcached、Netty 等。
这种模式也被叫做服务器的 1+M+N 线程模式,即使用该模式开发的服务器包含一个(或多个,1 只是表示相对较少)连接建立线程+M 个 IO 线程+N 个业务处理线程。这是业界成熟的服务器程序设计模式。
标签:知识点,Reactor,线程,SubReactor,IO,架构师,连接,Channel From: https://www.cnblogs.com/xieshier/p/16586530.html