Buffer表示缓冲区,用于nio中输入和输出存放和读取数据,他是一个数组,创建后就不能改变大小.

原来java.io的流操作在nio中就是对buffer操作.

*4个内部索引

---capacity,buffer的容量

int capacity()

---position,下一个要读/写的元素(从0开始),>=0 && <=limit

int position()   //回去当前position

Buffer position(int newPosition) //改变position的值,返回自身

---limit,第一个不可读/写元素,<=capacity

int limit()

Buffer limit(int newlimit)

---mark,作用是记录position,以便回退

final Buffer mark() {
    mark = position; //记录当前位置
    return this;
}
final Buffer reset() {
      int m = mark;
	if (m < 0)
	    throw new InvalidMarkException();
	position = m;    //将mark设置为position
	return this;
}

---确定关系

0<=mark<=position<=limit<=capacity  
---剩余字节数

boolean hasRemaining()

int remaining()

*创建buffer的4个静态方法

---ByteBuffer allocateDirect(int capacity)

这是ByteBuffer唯有的特性,使用系统能直接操作IO的存储空间作为缓存区,这样免去了java的buffer和系统buffer之间的数据复制.

注意,

1.DirectBuffer没有后援数组,故调用array(),arrayOffset()会抛异常.

2.系统或JVM不一定支持DirectBuffer

3.创建和销毁DirectBuffer,消耗更多的系统资源,故适合大量和长时间的IO需求

---ByteBuffer allocate(int capacity)

---ByteBuffer wrap(byte[] array)

创建指向array的引用,array被称为后援数组.

---ByteBuffer wrap(byte[] array, int offset, int length)

*Buffer操作

---clear()

position=0,limit =capacity

---flip(),写入数据前

limit=position,position=0

---rewind(),重新读取

limit不变,position=0

---compact()

将position和limit之间的数据复制到开始处.注,复制数据非常消耗系统资源.

//HeapByteBuffer.compact()实现代码
public ByteBuffer compact() {
	System.arraycopy(hb, ix(position()), hb, ix(0), remaining());
	position(remaining());
	limit(capacity());
	return this;
}
/* 
 * ByteBuffer.compact()注释中对compact的典型案例
 * buf.clear();          // Prepare buffer for use
 * while (in.read(buf) >= 0 || buf.position != 0) {
 *     buf.flip();
 *     out.write(buf);
 *     buf.compact();    // In case of partial write
 * }
 */

  

*buffer透视api,

含义:与原buffer共享一个后援数组,状态变量独立.见另一文章buffer view

---duplicate()

public ByteBuffer duplicate() {
   return new HeapByteBuffer(hb,  //共享同一个数组
			this.markValue(), //状态信息初始为this的值
			this.position(),
			this.limit(),
			this.capacity(),
			offset);
}

---slice(),将当前position到limit之间的空间作为新buffer的操作区域,一个切片操作

public ByteBuffer slice() {
  return new HeapByteBuffer(hb, //共享同一数组,array()返回同一值
			-1,u
			0,
			this.remaining(),
			this.remaining(),
			this.position() + offset); //offset从当前position开始
}
---asReadOnlyBuffer(),

与duplicate()功能相同,只是isReadOnly=true;

*总结

---buffer通过对外提供抽象方法,对内通过具体实现类实现的API设计方式,简洁安全的设计风格

---链式设计,代码简洁

---状态变量的设计,有创意

---慎用DirectBuffer和compact.

相关文章: