NIO总结

 

java.io 中最为核心的一个概念是流(Stream),面向流的编程。Java中,一个流要么是输入流,要么是输出流,不可能同时即是输入流又是输出流。


java.nio拥有3个核心概念: Selector,Channle与Buffer,在java.nio中,我们是面向块(block)或是缓冲区(buffer)编程的。Buffer本身就是一块内存,底层实现上,他实际上是个数组,数据的读、写通过Buffer来实现的。

java中的7种原生数据类型都有各自对应的Buffer类型,如IntBuffer,ByteBuffer等等,并没有BooleanBuffer类型

除了数组之外,Buffer还提供了了对于数据的结构化访问方式,并且可以追踪到系统的读写过程

Channel指的是可以向其写入数据或是从中读取数据的对象,它类似于java.io的Stream,所有数据的读写都是通过Buffer来进行的,永远不会出现直接向Channel写入的情况,或是直接从Channel读取数据的情况,与Stream不同的是,Channel是双向的,一个流只可能是InputStrem或是OutputStream,Channel打开后则可以进行读取、写入或是读写。

由于Channel是双向的,因此它能更好地反映出底层操作系统的真实情况:在Linux系统中,底层操作系统的通道就是双向的。


关于NIO Buffer中的3个重要状态属性的含义: position,limit与capacity。

capacity:buffer中能包含的元素的数量,不会为负数,永远也不会变化

limit   :无法再被读或者写的第一个元素位置的索引,这个数永远不会为负数,或是超过capacity的大小
 
position:buffer下一个读或者写的元素的位置索引,永远不会超过limit。


往Buffer读写元素有两种情况:1.一种是相对的读写元素之后position位置会发生变化
                                                 2.是绝对直接根据给定的索引位置读写元素,不会影响position

marking:标记一下元素的位置


resetting:position重新回到Markingb标记的位置

0<= mark <= position <= limit <= capacity

clear讲Buffer恢复初始化

flip读写操作转换

rewind 把position设置为0

Buffer不是线程安全的


Slice Buffer和原有buffer共享相同的底层数组

只读buufer,我们可以随时将一个普通的Buffer调用asReadOnlyBuffer方法返回一个只读Buffer,但不能将一个只读Buffer转换为读写Buffer



零拷贝

DirectByteBuffer 是直接在堆外内存存放数据,减少了一次拷贝。(如果从堆内内存直接进行与设备操作,如果此时发生GC,数据位置将被移动,发生报错,没办法让此时GC不发生。堆数据想与IO设备交流,要进行一次拷贝)

普通拷贝
首先用户空间像内核空间发出read()调用,内核空间访问磁盘,从磁盘把数据拷贝到内核空间,内核空间在拷贝到用户空间,执行逻辑代码(可无),然后用户空间向内核空间发出write()调用,数据从用户空间拷贝到内核空间数据缓冲区,在拷贝到socketChannel缓冲区,拷贝到协议引擎,write()返回
一共4次上下文切换,5次拷贝。

零拷贝(由操作系统提供)没有数据从内核空间复制到用户空间
首先用户空间发出sendfile()调用,访问磁盘,通过直接内存访问读取到内核空间的缓冲区。将数据写入到目标socket缓冲区(和前面不是同一个缓冲区),拷贝到协议引擎,接收返回信息,sendfile()调用返回。
一共2次上下文切换,3次拷贝
某些系统支持
首先用户空间发出sendfile()调用,访问磁盘,通过直接内存访问读取到内核空间的缓冲区。将数据的描述信息(内存地址,多长)写入到socket缓冲区(利用了Gathering),拷贝到协议引擎,接收返回信息,sendfile()调用返回。
一共2次上下文切换,2次拷贝

Scattering:把buffer对象弄成数组,读取数据
Gathering:把buffer对象弄成数组,写入数据
 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值