Java NIO是New IO还是Non-blocking IO

文章目录

前言

很多小伙伴对Java NIO的一些概念和编程不是很理解,希望通过本文对Java NIO与传统IO的对比,可以帮助大家更好地理解和掌握Java NIO。

NIO到底叫啥

Java NIO 有两种说法 ,一种是 New IO ,另一种是 Non-blocking IO(非阻塞IO)。

这两种说法都没毛病

从JDK 1.4开始,Java提供了一系列IO新特性 ,所以称之为New IO。而NIO提供了非阻塞的I/O操作方式,所以又可以称之为 Non-blocking IO。

通过对比理解NIO

相对于传统的 Java IO API,NIO API 不论是概念还是编程方式,对于开发人员来讲都没有那么的直观,理解起来比较困难。

(下面通过对比Java的传统IO和NIO编程,让小伙伴们轻松理解并掌握Java NIO。)

传统IO网络编程

在基于传统的Java IO API进行网络编程时,通过3个步骤就可以完成网络通信工作:

  1. 接受一个连接请求的Socket对象。
  2. 获取Socket关联的的输入/输出流。
  3. 读取输入流的数据或向输出流写入数据。

整个流程相对直观简单。示例代码如下图

NIO引入的新概念

而在Java NIO中,引入了一系列新的概念,比如通道(Channel )、缓冲区(Buffer )、选择器(Selector)等。

先来看一下这些概念:

  • 通道Channel):通道是连接数据源和缓冲区的桥梁。数据可以通过通道从数据源读取到缓冲区,或者从缓冲区写入到数据源。
  • 缓冲区Buffer):缓冲区是Java NIO中用于存储数据的核心组件。它是一个容器对象,用于存储要写入通道或从通道读取的数据。
  • 选择器Selector):选择器用于非阻塞I/O操作。它可以同时监控多个通道的状态(如是否准备好进行读或写操作),这使得开发者可以编写高效的、非阻塞的I/O代码。

这些概念给我的感觉就是:好像看了,又好像没看

对于初学者来说,在概念的转换和学习过程中可能会有一定的难度。所以还是要结合实际的例子来理解。

与上面相同的功能,看看利用Java NIO API是如何编写的。

NIO网络编程

两者区别

可以看到,完成网络通信的3个步骤依然存在,但是有几处代码不一样:

  1. SocketChannel替代了InputStream/OutputStream,既可以读又可以写。
  2. ByteBuffer替代了byte[],两者区别就是,ByteBuffer多了清除、标记、重置等功能,也是为什么说Java NIO 是面向缓冲区。
  3. 多了陌生的代码,比如,Selector.open()selector.select()xx.register(selector)等。

替代不难理解,主要是,这个Selector是什么?

这个Selector也就是Java NIO的核心组件,其工作模式就是《BIO、NIO、IO多路复用模型详细介绍&Java NIO 网络编程》说到的IO多路复用。

NIO的事件驱动

通过使用Selector,一个单独的线程可以去处理多个客户端的连接请求、读写操作。具体体现在以下几处:

  1. 第12行,注册 ServerSocketChannelSelector,并监听 ACCEPT 事件。这样意味着ServerSocket不用去accept()等待客户端的连接,而是交给了Selector去等待。
  2. 第33行,注册新连接到 Selector,并监听 READ 事件。 意味着,如果Socket数据没有准备好,由Selector去等待。

这样的话,只要是注册到Selector中的事件,不论多少个客户端的连接或输入输出,都会在selector.select()(第16行)统一由一个线程去阻塞等待。从而减少整体阻塞的次数,提高性能

总结

Java NIO 并不是完全非阻塞,只是通过事件驱动机制和缓冲区减少系统调用次数,减少了阻塞等待的时间。理解Java NIO需要重点理解事件驱动机制。

相关推荐
程序猿大波9 分钟前
基于Java,SpringBoot,Vue,HTML宠物相亲配对婚恋系统设计
java·vue.js·spring boot
云上空17 分钟前
C#初级知识总结
开发语言·c#
Leaf吧23 分钟前
分布式定时任务(xxl-job)
java·分布式
纪元A梦36 分钟前
华为OD机试真题——绘图机器(2025A卷:100分)Java/python/JavaScript/C++/C/GO最佳实现
java·javascript·c++·python·华为od·go·华为od机试题
钢铁男儿38 分钟前
C# 深入理解类:面向对象编程的核心数据结构
开发语言·数据结构·c#
24k小善1 小时前
FlinkSql入门与实践
java·大数据·flink·云计算
CodeCraft Studio1 小时前
Excel处理控件Spire.XLS系列教程:Java设置Excel活动工作表或活动单元格
java·python·excel
Doker 多克1 小时前
Python-Django系列—部件
开发语言·python
江沉晚呤时1 小时前
深入解析 ASP.NET Core 中的 ResourceFilter
开发语言·c#·.net·lucene
huangyuchi.1 小时前
【C++11】Lambda表达式
开发语言·c++·笔记·c++11·lambda·lambda表达式·捕捉列表