Netty四大组件之ByteBuf
ByteBuf作为Netty的数据容器,网络通信涉及到字节序列的移动。高效易用的数据结构必不可少。替换了Java NIO的ByteBuffer,主要是ByteBuf更加高效和易用,实现了自动扩容等等一些ByteBuffer不具备的功能
1. ByteBuf数据结构
ByteBuf的特点:
-
通过工具类Unpooled创建
-
索引随机访问
-
索引顺序访问
-
搜索操作
-
索引的Mark和Reset
-
派生缓冲区
-
ByteBuf和JDK ByteBuffer能够灵活的转换
在ByteBuf实现的中(AbstractByteBuf),维护了两个变量:
- readerIndex -- 读的当前索引位置
- writerIndex -- 写的当前索引位置
名称已 read
和 write
开头的 ByteBuf
方法, 将会推进对应的索引。而以 get
和 set
开头的则不会。 ByteBuf
默认真的最大容量为 Integer.MAX_VALUE
readXXX和writeXXX分别推进readerIndex和writeIndex。
2. ByteBuf操作
2.1 随机访问索引
通过 getBytes
系列接口来对ByteBuf进行随机访问。
ByteBuf buffer = Unpooled.buffer(3,3);
buffer.writeBoolean(true);
buffer.writeBoolean(true);
buffer.getBytes(0, new byte[1]);
System.out.println(buffer.readerIndex());
Tips: 用getBytes随机访问不会改变readerIndex
2.2 顺序访问索引
通过 readerIndex()
和 writerIndex()
获取读Index和写Index。
2.3 可丢弃字节
标记为可丢弃字节的分段包含了已经被读过的字节。通过调用 discardReadBytes()
方法, 可以丢弃它们并回收空间。这个分段的初始大小为 0,存储在 readerIndex 中,会随着 read 操作的执行而增加( get操作不会移动 readerIndex)。但是这个可以丢弃并不是字节把已经读的字段的字节不要了,而是把尚未读的字节数移到最开始。(这样做可能会导致内存复制)