参考:https://www.jianshu.com/p/89f927fe724f
缓冲区就是在内存中预留指定大小的存储空间对I/O数据作临时存储,这部分内存空间即为缓冲区。使用缓冲区可以减少动态分配和回数内存的次数。在java NIO中,缓冲区的作用也是用来临时存储数据。缓冲区可以看作通道(channel)与客户端(或服务器)的中转站,写入数据到channel或者从channel中读取数据,这样利于数据的高效读写。
所有缓冲区都有四个属性:capacity、limit、position、mark,并遵循:mark <= position <= limit <= capacity,以下是对四个属性的解释
java.nio.Buffer类是一个抽象类,不能被实例化。Buffer类的直接子类也不能被实例化,例如ByteBuffer。但是ByteBuffer类提供了4个静态工厂方法来获得ByteBuffer的实例:
方法 | 描述 |
---|---|
allocate(int capacity) | 从堆空间中分配一个容量大小为capacity的byte数组作为缓冲区的byte数据存储器 |
allocateDirect(int capacity) | 分配直接缓冲区,在缓冲区较大并长期存在,或者需要经常重用时,才使用这种缓冲区 |
wrap(byte[] array) | 这个缓冲区的数据会存放在byte数组中,bytes数组或buff缓冲区任何一方中数据的改动都会影响另一方。其实ByteBuffer底层本来就有一个bytes数组负责来保存buffer缓冲区中的数据,通过allocate方法系统会帮你构造一个byte数组 |
wrap(byte[] array,int offset, int length) | 在上一个方法的基础上可以指定偏移量和长度,这个offset也就是包装后byteBuffer的position,而length呢就是limit-position的大小,从而我们可以得到limit的位置为length+position(offset) |
ByteBuffer读写方法
方法 | 描述 |
---|---|
limit(), limit(10)等 | 读取和设置这4个属性的方法的命名和jQuery中的val(),val(10)类似,一个负责get,一个负责set |
reset() | 把position设置成mark的值,相当于之前做过一个标记,现在要退回到之前标记的地方 |
clear() | position = 0;limit = capacity;mark = -1; 有点初始化的味道,但是并不影响底层byte数组的内容 |
flip() | limit = position;position = 0;mark = -1; 翻转,也就是让flip之后的position到作准备limit这块区域变成之前的0到position这块,翻转就是将一个处于存数据状态的缓冲区变为一个处于准备取数据的状态 |
get() | 相对读,从position位置读取一个byte,并将position+1,为下次读写作准备 |
作者:ZMRWEGo
链接:https://www.jianshu.com/p/89f927fe724f
来源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。