Java NIO基本概念+样例

——简介

Java NIO(New IO——新IO,NON Blocking IO——非阻塞IO),从Java1.4版本开始引入的一个新的IO API,可以代替Java IO API。NIO与原来的IO有同样的作用和目的,但是使用方式完全不同,NIO支持面向缓冲区的、基于通道的IO操作。NIO将以更加高效的方式进行文件的读写操作。

NIO与IO的主要区别

在这里插入图片描述

通道和缓冲区

在这里插入图片描述

  • Java NIO核心:通道(Channel)和缓冲区(Buffer)。通道表示打开到IO设备(例如:文件、套接字)的连接。若需要N使用NIO系统,需要获取用于连接IO设备的通道以及用于容纳数据的缓冲区。然后操作缓冲区,对数据进行处理。简而言之:Channel用于传输,Buffer负责存储。

通道:用于源节点和目标节点的连接。在Java NIO中负责缓冲区中数据的传输。Channel本身不存储数据,因此需要配合缓冲区进行传输

  • 主要实现类Channel接口:
    • FileChannel:本地文件通道
    • SocketChannel:网络
    • ServerSocketChannel
    • DatagramChannel
  • 获取通道:
    • 本地IO:FileInputStream/FileOutputStream
    • 网络IO:Socket、ServerSocket、DatagramSocket
    • 针对各个通道提供了静态方法open()
    • Files工具类的newByteChannel()

缓冲区:在Java NIO中负责数据的存取。缓冲区就是数组。用于存储不同类型的数据。

  • 根据数据类型的不同(boolean除外),提供相应类型的缓冲区:ByteBuffer、CharBuffer、ShortBuffer、IntBuffer、LongBuffer、FloatBuffer、DoubleBuffer
  • 缓冲区管理的方法几乎一致,通过allocate()获取缓冲区
  • 两个核心方法
    • put:存入数据到缓冲区内
    • get:获取缓冲区的数据
    • 其他方法:
      • flip:切换成读模式
      • rewind:可重复读
      • clear:清空缓冲区,但是缓冲区中的数据依旧存在,只是处于一种被遗忘的状态
  • 四个核心属性
    • capacity:容量,表示缓冲区中最大存储数据的容量。一旦声明不可改变
    • limit:界限,表示缓冲区中可以操作数据的大小。limit后数据不能进行读写
    • position:位置,表示缓冲区中正在操作数据的位置
    • mark:标记,记录当前position的位置,可以通过reset恢复到mark的位置
    • 0<=mark<=position<=limit<=capacity

直接缓冲区和非直接缓冲区

  • 非直接缓冲区:通过allocate()方法分配缓冲区,将缓冲区建立在JVM内存中
  • 直接缓冲区:通过allocateDirect()方法分配直接缓冲区,将缓冲区建立在物理内存中。可以提高效率。

分散Scatter和聚集Gather

  • 分散读取(Scatter Reads):是指从Channel中读取的数据“分散”到多个Buffer中(按照缓冲区的顺序,从Channel中读取的数据依次将Buffer填满
  • 聚集写入(Gather Writes):是指将多个Buffer中的数据“聚集”到Channel(按照缓冲区的顺序,写入position和limit之间的数据到Channel

字符集Charset

  • 编码:字符串 ——》字节数组
  • 解码:字节数组——》字符串

——阻塞和非阻塞

使用NIO完成通信的三个核心

  • 通道(Channel):负责连接
    • java.nio.Channels.Channel接口
      • SelectableChannel
        • SocketChannel
        • ServerSocketChannel
        • DatagramChannel
  • 缓冲区(Buffer):负责存储数据
  • 选择器(Selector):是SelectableChannel的多路复用器。用于监控SelectableChannel的IO状况。利用 Selector可使一个单独的线程管理多个 Channel。Selector 是非阻塞 IO 的核心

SelectionKey
当调用 register(Selector sel, int ops) 将通道注册选择器时,选择器对通道的监听事件,需要通过第二个参数 ops 指定。
可以监听的事件类型(用 可使用 SelectionKey 的四个常量 表示):

  • 读 : SelectionKey.OP_READ (1)
  • 写 : SelectionKey.OP_WRITE (4)
  • 连接 : SelectionKey.OP_CONNECT (8)
  • 接收 : SelectionKey.OP_ACCEPT (16)
    若注册时不止监听一个事件,则可以使用“位或”操作符连接。

DatagramChannel:Java NIO中的DatagramChannel是一个能收发UDP包的通道。

管道 (Pipe)
Java NIO 管道是2个线程之间的单向数据连接。Pipe有一个source通道和一个sink通道。数据会被写到sink通道,从source通道读取。
在这里插入图片描述
样例代码:https://github.com/xulejun/nio-demo

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

程序少年不秃头

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值