ByteBuf

                                ByteBuf是netty传输数据的容器,是对jdk ByteBuffer的增强

1.ByteBuf的创建

//使用ByteBufAllocator创建空参创建默认的容量为256,也可以自己指定大小,创建时指定 默认是直接内存
ByteBuf buffer = ByteBufAllocator.DEFAULT.buffer();
System.out.println(buffer);

2.直接内存和堆内存

//创建在堆内存的ByteBuf
ByteBuf buf = ByteBufAllocator.DEFAULT.heapBuffer();
//创建在直接内存的ByteBuf
ByteBuf buf1 = ByteBufAllocator.DEFAULT.directBuffer();

3.池化与非池化

将ByteBuf池化起来,默认创建的就是使用了池化功能

4.ByteBuf的组成

5.ByteBuf写入

 

6.扩容

      扩容是指在ByteBuf在写入数据时,已经超过容量但没有超过最大容量

     在容量小于512时,会选择16的整数倍进行扩容超过512时则会选择2^n扩容

     比如容量为12,写入数据在13的位置,容量会扩容到16,写出位置在17容量会扩容到32

     写入位置在514容量会扩容到1024,写入位置在1026,容量会扩容到2048.......以此类推 

 

 

 7.读取

 

 

 读取方法比较简单,直接调用buf的readxxx()方法即可

 8.内存释放

ByteBuf的内存释放是通过ReferenceCounted来实现的(采用的是引用计数的算法来回收内存)

io.netty.util.ReferenceCounted
package io.netty.util;

public interface ReferenceCounted {
   /**
     * Increases the reference count by {@code 1}.
     * 此方法是将bytebuf的引用加1
     */
   ReferenceCounted retain();


   /**
     * Decreases the reference count by {@code 1} and 
                deallocates this object if the reference count reachesat
     * {@code 0}.
     * 此方法是将bytebuf的引用-1
     * @return {@code true} if and only if the reference count 
         became {@code 0} and this object has been deallocated
     */
    boolean release();
}

当bytebuf的引用计数为0时就会回收调用改bytebuf(不同会有不同的回收算法池化的会入池,非池化的会执行回收内存(直接内存回收和堆内存回收))

 

9.零拷贝

    ByteBuf的slice(int index,intlength);

他是将一个bytebuf按照指定的索引切,切多长的一个buf。内部使用的是同一个内存的buf。用新的指针来指向切出来的buf。

所以在改变一个buf的同时。另一个buf的内容也会改变

(注意,切出来的buf不允许往里添加新的内容,释放了原有的buf的内容后会影响切出来的buf)

  duplicate()方法是直接将整个buf的读写指针复制一份(使用的还是同一块内存)

  想要真正的复制就使用copy相关的方法

compositeByteBuf

创建 

CompositeByteBuf buf = ByteBufAllocator.DEFAULT.compositeBuffer();

//在逻辑上将几个Bytebuf组合在一起

//带上一个boolean参数的方法,自动计算读写指针,不然读写指针还是为0

buf.addComponents(true,buf1,buf2);

 

posted @ 2022-05-17 15:06  wangkunlaile  阅读(199)  评论(0)    收藏  举报