NIO编程学习笔记(一)
NIO的概述
简介
NIO全称是non-blocking io,即非阻塞IO。
Java NIO(New IO)是从Java 1.4版本开始引入的一个新的IO API,可以替代标准的Java IO API。NIO与原来的IO有同样的作用和目的,但是使用的方式完全不同,NIO支持面向缓冲区的、基于通道的IO操作。NIO将以更加高效的方式进行文件的读写操作。
IO与NIO的区别
IO | NIO |
---|---|
面向流(Stream Oriented) | 面向缓冲区(Buffer Oriented) |
阻塞IO(Blocking IO) | 非阻塞IO(NonBlocking IO) |
选择器(Selectors) |
什么是面向流?什么是面向缓冲区?
传统IO在传输数据时,根据输入输出的不同需要分别建立不同的链接,而且传输的数据是以流的形式在链接上进行传输的。
就像自来水要通过水管将自来水厂和家连接起来一样,如图:
NIO在传输数据时,会在输入输出端之间建立通道,然后将数据放入到缓冲区中。缓冲区通过通道来传输数据
这里通道就像是铁路,能够连通两个地点。缓冲区就像是火车,能够真正地进行数据的传输。
简单的来说就是不用建立两个通道了。
NIO的三大组件
Channel(通道)&&Buffer(缓冲区)
NIO有三大组件,其中最为核心的就是Channel和Buffer。
Channel有一点类似于Stream,它就是读写数据的双向通道,可以从Channel将数据读入Buffer,也可以将Buffer的数据写入Channel,而之前的Stream要么是输入,要么是输出,Channel要比Stream更加底层。
简而言之就是,通道负责传输,缓冲区负责存储。
常见的Channel有:
- FileChannel
- DatagramChannel
- SocketChannel
- ServletSocketChannel
常见的Buffer有:
- ByteBuffer(MappedByteBuffer、DirectByteBuffer、HeapByteBuffer)
- CharBuffer
- ShortBuffer
- IntBuffer
- LongBuffer
- FloatBuffer
- DoubleBuffer
Selector(选择器)
用选择器来形容它可能会有一点抽象。
最初我们开发服务器的时候是使用多线程进行设计的。
缺点:
-
内存占用高
-
线程上下文切换成本高
-
只适合连接数少的场景
之后我们引入了线程池的概念
缺点:
-
阻塞模式下,线程仅能处理一个 socket 连接
-
仅适合短连接场景
Selector设计服务器
selector 的作用就是配合一个线程来管理多个 channel,获取这些 channel 上发生的事件,这些 channel 工作在非阻塞模式下,不会让线程吊死在一个 channel 上。适合连接数特别多,但流量低的场景(low traffic)
案例实现(三大组件的基本使用)
简单的使用了一下
public class NIO_demo01 {
public static void main(String[] args) {
try {
// 文件的channel作为数据的读写通道
FileChannel channel = new FileInputStream("data.txt").getChannel();
//准备缓冲区 allocate() 缓冲区大小
ByteBuffer buffer = ByteBuffer.allocate(10);
while (true) {
// 从channel读取数据,向buffer写入
int len = channel.read(buffer);
// 没有内容了
if (len == -1) {
break;
}
// 切换至读模式
buffer.flip();
// 检查是否有剩余的数据
while (buffer.hasRemaining()) {
// 一次读一个字节
byte b = buffer.get();
System.out.println((char)b);
}
// 切换为写模式
buffer.clear();
}
}
catch (IOException e) {
e.printStackTrace();
}
}
}
可以实现从本地的data.txt文件中读取数据。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 全程不用写代码,我用AI程序员写了一个飞机大战
· DeepSeek 开源周回顾「GitHub 热点速览」
· 记一次.NET内存居高不下排查解决与启示
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· .NET10 - 预览版1新功能体验(一)