BIO NIO AIO详解

Java BIO NIO AIO详解

同步,异步,阻塞,非阻塞

这几个概念理解起来确实比较困难,特别是同步和阻塞,异步和非阻塞。首先要明确的一个概念是同步和异步主要是关注的是消息通信机制,所以同步和异步主要是关注客户端和服务端两个方面的消息如何通信。而阻塞和非阻塞主要是等待调用结果时的状态,所以关注的主要是当前线程在等待结果时能够做什么,如果在等待结果时当前线程能够做其他的事,则线程是非阻塞的;如果只能等待返回结果,则当前线程是阻塞的。下面举个例子来具体说明一下:
比如你跟书店老板打电话,确认是否书店中有哈利波特这本书。书店老板电话没有挂断,说你等一下,我现在查一下,你一直在等待,此时就是一种同步通信。而如果老板说我晚点电话通知你,然后挂断电话,此时就是异步通信。
让我们在换一个视角,还是打电话确定是否有哈利波特这本书这件事情。在打电话的过程中,你什么都没有干,只是一直在等待,那么此时你就是处于阻塞状态。而如果此时你正在看电视,此时你就是非阻塞状态,但是需要不定时的检查一下电话那边有没有回复。

所谓同步,就是在发出一个调用时,在没有得到结果之前,该调用就不返回。但是一旦调用返回,就得到返回值了。换句话说,就是由调用者主动等待这个调用的结果.
而异步则是相反,调用在发出之后,这个调用就直接返回了,所以没有返回结果。换句话说,当一个异步过程调用发出后,调用者不会立刻得到结果。而是在调用发出后,被调用者通过状态、通知来通知调用者,或通过回调函数处理这个调用。
阻塞调用是指调用结果返回之前,当前线程会被挂起。调用线程只有在得到结果之后才会返回。非阻塞调用指在不能立刻得到结果之前,该调用不会阻塞当前线程。
在IO操作中,有以下四种组合:

  1. 同步阻塞IO:调用者发起IO操作请求,等待IO操作完成(阻塞)。IO操作的过程需要等待,等待服务端返回结果,操作执行完成后返回结果(同步)
  2. 同步非阻塞:调用者发起IO操作请求,询问IO操作的的状态,如果未完成,则立即返回;如果完成,则返回结果(非阻塞)。IO操作的过程需要等待执行完成才返回结果(同步)
  3. 异步阻塞:调用者发起IO操作请求,等待IO操作完成在返回(阻塞)。IO操作的过程不需要等待,操作完成后通过通知或者回调获取结果(异步)
  4. 异步非阻塞:调用者发起IO操作请求,询问IO操作的状态,如果未完成,则立即返回;如果完成,则返回结果(非阻塞)。IO操作的过程不需要等待,操作完成后通过通知或回调获得结果(异步)
    在下面的具体介绍中,我会进行具体的说明。

Java IO 操作类

Java中进行IO操作的类一般分为以下四类:

  1. 字节流的输入和输出:InputStream和OutputStream
  2. 字符流的输入和输出
  3. 网络编程Socket

BIO

首先BIO是同步阻塞调用。阻塞是因为服务端在调用accept方法时,服务端会一直阻塞在accept方法上,直到在对应的端口上接收到数据;同步是因为客户端会一直等待服务端执行完成才返回结果。可以想一下JavaScript中的Ajax请求,在异步Ajax请求发出后,浏览器会执行接下来的JS代码,直到服务端发回处理结果,然后执行对应的回调函数。这是典型的异步请求。

NIO

NIO(New IO or Non-Block IO)是一种同步非阻塞的通信模式。NIO客户端和服务器之间通过Channel通信。NIO可以在Channel进行读写操作。这些Channel都会被注册在Selector多路复用器上。Selector通过一个线程不停的轮询这些Channel。找出已经准备就绪的Channel执行IO操作。说是非阻塞是因为NIO通过一个线程轮询,实现千万个客户端的请求。说是同步是因为客户端一直在等待服务端执行完成才返回结果。

AIO

总结

参考链接