Java NIO 总结

NIO与原IO的区别


  • 原来的IO和NIO最大的区别在于数据打包和传输的方式。原来的IO是基于流的方式处理数据,而NIO是基于块的方式处理数据。
  • NIO适用于使用少数线程处理大量连接的情况

Java NIO的核心


  • Channels
  • Buffers
  • Selectors

Java NIO通过事件驱动的方式监听消息,实际上是采用了Reactor模式。各部分的关系如图:
Java NIO 组成结构

Channel


  1. 重要的实现
    1. FileChannel:无法设置为非阻塞模式,总是运行在阻塞模式下
    2. DatagramChannel:收发UDP数据包的通道
    3. SocketChannel:TCP连接客户端通道,可以设置为非阻塞
    4. ServerSocketChannel:TCP连接服务端通道,可以设置为非阻塞
  2. 特点
    1. 既可以从通道中读数据到缓冲区,也可以从缓冲区中写数据到通道;通道支持异步的读写
    2. 支持Buffer的Scatter和Gather操作

Buffer


  1. 重要的实现
    1. 八种中基本数据类型的Buffer
    2. MappedByteBuf,用于表示内存映射文件,直接内存方式,速度比较快
  2. 特点
    1. Buffer的读、写模式是相互对立的,进行反转需要调用flip()方法
    2. Buffer的工作原理:capacity,limit,position,需要了解读和写情况下的意义

Selectors


  1. 一个Selector能够检测多个Channel
  2. Channel需要在Selector上注册自己感兴趣的事件,事件主要有:Connect,Accept,Read,Write
  3. 调用Selector的select方法阻塞等待Channel上的特定事件就绪
  4. select()返回准备就绪的通道个数,调用selector.selectedKeys()返回已经准备就绪的事件
  5. 在Selector的open方法中,会根据不同的操作系统提供不同的内部实现,如果是Linux操作系统,则使用Poll(kernel < 2.6)、epoll(kernel > 2.6);如果是window操作系统,则是select,如果是Unix,则是kqueue

Selector的唤醒底层实现


Selector在open()的时候,会建立一个Pipe,通过Pipe实现唤醒。具体参考《Nio Selector阻塞唤醒原理
1. Window下不支持使用Pipe,所以通过两个连接的SocketChannel实现了Pipe,通过本地地址127.0.0.1自己连接自己
2. Linux下则直接使用系统的Pipe进行通信。

Java NIO的缺点


  • 需要自己处理半包和粘包问题。当从通道中读数据到缓冲区的时候,我们并不知道缓冲区中的内容是否是一个完整的包,需要自己手动的进行处理。
  • 这些问题可以通过Netty进行解决
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值