【Netty】 ByteBuf的常用API总结
目录
一、ByteBuf介绍
二、ByteBuf创建
1.池化创建 ByteBufAllocator
2.Unpooled (非池化)创建ByteBuf
3.ByteBufUtil 操作ByteBuf
三、读取ByteBuf数据
1.get方法
2.read方法
3.set方法
4.write方法
5.索引管理
6.索引查找
7.索引查找
8.其他方法
本篇主要介绍ByteBuf的常用操作API,Netty性能的卓越表现离不开ByteBuf的巧妙设计,它提供了一系列的缓冲区读写方法,另外为了方便起见还特定义了ByteBufUtil,提供了比较丰富的操作ByteBuf方法。
一、ByteBuf介绍
为了提高性能,Netty重新设计了字节缓冲区ByteBuf,类似Java Nio的ByteBuffer,但工作方式略有区别,比后者更加灵活、高效。
ByteBuf有几个重要属性:
capacity:容量;
0:缓冲区开始位置;
readIndex:下一个读位置;
writeIndex:下一个写位置;
一个ByteBuf对象即可像byte数组一样工作,又可以像IO字节流一样工作。当前的可读数据区是[readIndex,writeIndex);可写区是[writeIndex,capacity);而[0,readIndex)区间的字节是可废弃数据(Discardable),如下图所示:
+-------------------+------------------+------------------+
| discardable bytes | readable bytes | writable bytes |
| | (CONTENT) | |
+-------------------+------------------+------------------+
| | | |
0 <= readerIndex <= writerIndex <= capacity
基本的操作包括
1.从ByteBuf中读取数据,从readerIndex开始向后读取需要的字节数,readerIndex随之改变;
2.向ByteBuf中写数据,从writeIndex开始向后写数据,同时writeIndex随之改变;
3.删除ByteBuf已读数据,从[0,readerIndex)为已读完的数据,为了节省空间需要释放内存,释放示意图如下:
* BEFORE discardReadBytes()** +-------------------+------------------+------------------+* | discardable bytes | readable bytes | writable bytes |* +-------------------+------------------+------------------+* | | | |* 0 <= readerIndex <= writerIndex <= capacity*** AFTER discardReadBytes()** +------------------+--------------------------------------+* | readable bytes | writable bytes (got more space) |* +------------------+--------------------------------------+* | | |* readerIndex (0) <= writerIndex (decreased) <= capacity
4.清空ByteBuf数据,不需要清空数据,通过移动两个指针readerIndex和writeIndex,指向0即可。
* BEFORE clear()** +-------------------+------------------+------------------+* | discardable bytes | readable bytes | writable bytes |* +-------------------+------------------+------------------+* | | | |* 0 <= readerIndex <= writerIndex <= capacity*** AFTER clear()** +---------------------------------------------------------+* | writable bytes (got more space) |* +---------------------------------------------------------+* | |* 0 = readerIndex = writerIndex <= capacity
二、ByteBuf创建
1.池化创建 ByteBufAllocator
即PooledByteBufAllocator
获取ByteBufAllocator,通过以下两种方式获取
//方法1
Channel channel = ...;
ByteBufAllocator allocator = channel.alloc();
//方法2
ChannelHandlerContext ctx = ...;
ByteBufAllocator allocator2 = ctx.alloc();
ByteBufAllocator中创建byteBuf的方法如下
方法名称 | 方法描述 |
buffer() buffer(int) buffer(int, int) | Return a ByteBuf with heap-based or direct data storage |
heapBuffer() heapBuffer(int) heapBuffer(int, int) | Return a ByteBuf with heap-based storage. |
directBuffer() directBuffer(int) directBuffer(int, int) | Return a ByteBuf with direct storage. |
compositeBuffer() compositeBuffer(int) heapCompositeBuffer() heapCompositeBuffer(int) directCompositeBuffer() directCompositeBuffer(int) | Return a CompositeByteBuf that can be expanded by adding heapbased or direct buffers. |
ioBuffer() | Return a ByteBuf that will be used for I/O operations on a socket. |
2.Unpooled (非池化)创建ByteBuf
即UnPooledByteBufAllocator
当未引用 ByteBufAllocator 时,上面的方法无法访问到 ByteBuf。对于这个用例 Netty 提供一个实用工具类称为 Unpooled,,它提供了静态辅助方法来创建非池化的 ByteBuf 实例,方法如下:
方法名称 | 方法描述 |
buffer() buffer(int) buffer(int, int) | Returns an unpooled ByteBuf with heap-based storage |
directBuffer() directBuffer(int) directBuffer(int, int) | Returns an unpooled ByteBuf with direct storage |
wrappedBuffer() | Returns a ByteBuf, which wraps the given data. |
copiedBuffer() | Returns a ByteBuf, which copies the given data |
3.ByteBufUtil 操作ByteBuf
三、读取ByteBuf数据
get/read get不会改变读索引,read会改变读索引
1.get方法
方法名称 | 方法描述 |
getBoolean(int) | 返回当前索引的 Boolean 值 |
getByte(int) getUnsignedByte(int) | 返回当前索引的(无符号)字节 |
getMedium(int) getUnsignedMedium(int) | 返回当前索引的 (无符号) 24-bit 中间值 |
getInt(int) getUnsignedInt(int) | 返回当前索引的(无符号) 整型 |
getLong(int) getUnsignedLong(int) | 返回当前索引的 (无符号) Long 型 |
getShort(int) getUnsignedShort(int) | 返回当前索引的 (无符号) Short 型 |
getBytes(int, ...) | 字节 |
2.read方法
方法名称 | 方法描述 |
readBoolean() | 返回当前索引的Boolean值,读索引加一 |
readByte() readUnsignedByte() | 返回当前索引的(无符号)字节,读索引加一 |
readMedium() readUnsignedMedium() | 返回当前索引的 (无符号) 24-bit 中间值,读索引加3 |
readInt() readUnsignedInt() | 返回当前索引的(无符号) 整型,读索引加4 |
readLong() readUnsignedLong() | 返回当前索引的 (无符号) Long 型,读索引加8 |
readShort() readUnsignedShort() | 返回当前索引的 (无符号) Short 型,读索引加2 |
readBytes(int,int, ...) | 返回当前位置到length得到一个字节数组,读索引加length |
3.set方法
方法名称 | 方法描述 |
setBoolean(int, boolean) | 在指定的索引位置设置 Boolean 值 |
setByte(int, int) | 在指定的索引位置设置 byte 值 |
setMedium(int, int) | 在指定的索引位置设置 24-bit 中间 值 |
setInt(int, int) | 在指定的索引位置设置 int 值 |
setLong(int, long) | 在指定的索引位置设置 long 值 |
setShort(int, int) | 在指定的索引位置设置 short 值 |
4.write方法
方法名称 | 方法描述 |
writeBoolean(boolean) | 在指定的索引位置设置 Boolean 值,写索引加一 |
writeByte(int) | 在指定的索引位置设置 byte 值,写索引加一 |
writeMedium(int) | 在指定的索引位置设置 24-bit 中间 值,写索引加3 |
writeInt(int) | 在指定的索引位置设置 int 值,写索引加4 |
writeLong(long) | 在指定的索引位置设置 long 值,写索引加8 |
writeShort(int) | 在指定的索引位置设置 short 值,写索引加2 |
writeBytes(int,...) | 在当前索引写入一个Byte数组,写索引加数组长度 |
5.索引管理
方法名称 | 方法描述 |
markReaderIndex(), markWriterIndex() | 标记读(写)索引 |
resetReaderIndex() resetWriterIndex() | 读(写)索引回到mark标记的索引值 |
readerIndex(int) writerIndex(int) | 将读(写)索引设置到指定位置 |
clear() | 可以同时设置 readerIndex 和 writerIndex 为 0。这不会清除内存中的内容 |
6.索引查找
方法名称 | 方法描述 |
for EachByte(ByteBufProcessor.FIND_NUL) | 查找byte,返回byte的索引 |
7.索引查找
方法名称 | 方法描述 |
duplicate() slice(int, int) | 所有这些都返回一个新的 ByteBuf 实例包括它自己的 reader, writer 和标记索引。然而,内部数据存储共享就像在一个 NIO 的 ByteBuffer |
copy() copy(int, int) | 返回的 ByteBuf 有数据的独立副本 |
8.其他方法
方法名称 | 方法描述 |
isReadable() | 返回是否有字节可读 |
isWritable() | 返回是否可以写 |
readableBytes() | 返回可以读的字节长度 |
writablesBytes() | 返回可以写的字节长度 |
capacity() | 返回byteBuf的容量 |
maxCapacity() | 返回byteBuf可以有的最大容量 |
hasArray() | 如果byteBuf可以直接返回一个数组就返回true (heap buf才会为true) |
array() | hasArray返回true,该方法就会返回一个数组 |
参考资料
ByteBuf的常用API总结
Netty详解之九:ByteBuf介绍
相关文章:
【Netty】 ByteBuf的常用API总结
目录 一、ByteBuf介绍 二、ByteBuf创建 1.池化创建 ByteBufAllocator 2.Unpooled (非池化)创建ByteBuf 3.ByteBufUtil 操作ByteBuf 三、读取ByteBuf数据 1.get方法 2.read方法 3.set方法 4.write方法 5.索引管理 6.索引查找 7.索引查找 8.其…...
热门敏捷开发管理工具
敏捷管理研发工具可以协助团队更好地进行敏捷开发和管理。以下是几种流行的敏捷管理研发工具: Leangoo:Leangoo领歌一款永久免费的专业敏捷研发管理工具,它覆盖了敏捷项目研发全流程,包括小型团队敏捷开发,规模化敏捷…...
Java分支结构:一次不经意的选择,改变了我的一生。
👑专栏内容:Java⛪个人主页:子夜的星的主页💕座右铭:前路未远,步履不停 目录 一、顺序结构二、分支结构1、if语句2、switch语句 好久不见!命运之轮常常在不经意间转动,有时一个看似微…...
Unity中Shader需要了解的点与向量
文章目录 前言一、点和向量的区别二、向量加法减法1、向量加法2、向量减法(可以把向量减法转化为向量加法) 三、向量的模四、标量![在这里插入图片描述](https://img-blog.csdnimg.cn/03df81df3cdf47989a11605d5f5e7da5.png)1、向量与标量的乘法 前言 Unity中Shader了解使用的…...
Java初始化大量数据到Neo4j中(一)
背景:我们项目第一次部署图数据库,要求我们把现有的业务数据以及关系上线第一时间初始化到Neo4j中。开发环境数据量已经百万级别。生成环境数据量更多。 我刚开始开发的时候,由于对Neo4j的了解并没有很多,第一想到的是用代码通用组…...
Excel·VBA日期时间转换提取正则表达式函数
标准日期转换 Function 标准日期(ByVal str$) As DateDim pat$, result$arr Array("(\d{4}).*?(\d{1,2}).*?(\d{1,2})", "(\d{4}).*?(\d{1}).*?(\d{1,2})")If Len(str) < 8 Then pat arr(1) Else pat arr(0)With CreateObject("vbscript.r…...
Django中的缓存
Django中的缓存 缓存的定义 定义: 缓存是-类可以更快的读取数据的介质统称,也指其它可以加快数据读取的存储方式。一般用来存储临时数据,常用介质的是读取速度很快的内存 意义:视图渲染有一定成本,数据库的频繁查询过高;所以对于低频变动的页…...
Python 编程基础 | 第二章-基础语法 | 2.4、while 语句
一、while 语句 1、循环语句 Python 编程中 while 语句用于循环执行程序,其基本形式为: while 判断条件(condition):执行语句(statements)……例如: count 0 while (count < 9):print(count)count 1while 语句时还有另外两个…...
Qt Charts简介
文章目录 一.图标类型Charts分类1.折线图和样条曲线图2.面积图和散点图3.条形图4.饼图5.误差棒图6.烛台图7.极坐标图 二.坐标轴Axes类型分类三.图例四.图表的互动五.图表样式主题 一.图标类型Charts分类 图表是通过使用系列类的实例并将其添加到QChart或ChartView实例来创建的…...
MinGW、GCC、GNU和MSVC是什么?有什么区别?
在C和C开发中,常常会遇到MinGW、GCC、GNU和MSVC这些术语。本教程将向您解释它们的含义以及它们之间的区别,帮助您更好地理解这些常见的编译工具和开发环境。 MinGW(Minimalist GNU for Windows): MinGW是一个开源的软件…...
引入easyExcel后,导致springboot项目无法开启tomcat
报错信息: Caused by: java.lang.annotation.IncompleteAnnotationException: org.terracotta.statistics.Statistic missing element type at sun.reflect.annotation.AnnotationInvocationHandler.invoke(AnnotationInvocationHandler.java:81) at com.sun.proxy…...
Doris数据库FE——启动流程源码详细解析
Doris中FE主要负责接收和返回客户端请求、元数据以及集群管理、查询计划生成等工作。代码路径:doris/fe/fe-core/src/main/java/org/apache/doris/DorisFE.java 环境检查 在启动FE的时候,主要做环境检查。检查一些启动时必要的环境变量以及初始化配置…...
服务断路器_Resilience4j线程池隔离实现
线程池隔离配置修改YML文件 resilience4j:thread-pool-bulkhead: instances:backendA:# 最大线程池大小maxThreadPoolSize: 4# 核心线程池大小coreThreadPoolSize: 2# 队列容量queueCapacity: 2编写controller /*** 测试线程池服务隔离* return*/Bulkhead(name "backe…...
原神启动原神启动原神启动原神启动
测试游戏抽卡场景是确保玩家可以正常抽取虚拟物品或角色的重要部分。以下是一些可能的游戏抽卡场景的测试用例示例: 1.正常抽卡流程: 2.测试用户是否能够成功进行一次或多次抽卡操作。 3.确保每次抽卡后,用户收到相应的物品或角色。 4.抽卡…...
Glide - Android的图像加载和缓存库,专注于平滑滚动
官网 GitHub - bumptech/glide: An image loading and caching library for Android focused on smooth scrolling 项目介绍 An image loading and caching library for Android focused on smooth scrolling Glide is a fast and efficient open source media management a…...
如何使用 API 接口获取商品数据,从申请 API 接口、使用 API 接口到实际应用,一一讲解
在当今的数字化时代,应用程序接口(API)已经成为数据获取的重要通道。API 接口使得不同的应用程序能够方便地进行数据交换,从而促进了信息的广泛传播和利用。在众多的数据源中,商品数据是一个非常重要的领域,…...
苹果 CMS 原生 Java 白菜影视 App 源码【带打包教程】
苹果 CMS 原生 Java 白菜影视 App 源码是一款功能强大的影视应用程序,支持画中画、投屏、点播、播放前广告和支持普通解析等多种功能。与萝卜 App 源码相比,该套源码更加稳定,且拥有画中画投屏和自定义广告等功能,提高了安全性。 …...
Flutter开发之Package与Plugin
前言 在flutter中有包和插件两个概念,插件 (plugin) 是 package 的一种,全称是 plugin package,我们简称为 plugin,中文叫插件。包(Package)主要指对flutter相关功能的封装,类似于Android中的插件和iOS中的三方库。而插…...
[极客大挑战 2019]RCE ME 取反绕过正则匹配 绕过disable_function设置
目录 取反 1.蚁剑插件绕过 2.baypass disable_function open_dir/disable_function putenv()/LD_PRELOAD 来绕过限制 利用条件 利用思路 有意思。。。。 <?php error_reporting(0); if(isset($_GET[code])){$code$_GET[code];if(strlen($code)>40){die("Th…...
硬盘接口随机
关于硬盘接口 1 首先,关于[物理接口、协议、通道]2 物理接口:通讯中的电,光口,“物理规格,像是公路、铁路”。通道:通讯协议中的应用层以下所有层?“县道,省道,高速&am…...
芯片测试方案之如何测试芯片EN输入阈值?
在电源管理芯片的设计中,除了常规的VIN、VOUT以及GND端口之外,还会有SW、EN、FB等芯片独有的特殊端口引脚,这些引脚或负责电源开关的输入,或负责电路的反馈电压/电流,这些引脚在芯片的工作中有着极其重要的作用&#x…...
screenOrientation的值
在 Android 应用程序中,android:screenOrientation 属性可以设置为多个不同的值,以控制活动的屏幕方向。以下是一些常用的 android:screenOrientation 的值: "unspecified":这是默认值,表示系统会根据设备的…...
为什么SQL预编译可以防止SQL注入攻击
前言 防范SQL注入攻击是每一位做后端开发的程序员必须会的基本功。本文介绍其中一种防范攻击的方法:SQL预编译。 本文大部分内容引用自这篇文章,部分内容有修改。 注入例子 先简单回顾下SQL注入攻击的过程,假设有一个SQL语句: …...
基于体系结构-架构真题2022(四十一)
给定关系模式R(U,F),其中U为属性集,F是U上的一组函数依赖,那么函数依赖的公理系统中分解规则是指()为F所蕴含。 解析: 伪传递是x到y,wy到z,则xw到z 传递是z…...
【uniapp+vue3 】页面加载时根据不同角色设置导航栏标题
uniapp 页面加载时根据不同角色设置导航栏标题 其实很好实现,第一次开发uniapp项目,所以什么都不懂,绕了一点点的弯路 在对应页面的onLoad中获取到跳转过来传的参数中的判断角色字段,我这里传的是getRole uni.setNavigationBarT…...
不讲故事的设计模式-模板方法模式
文章目录 模板方法模式简介作用模板方法模式的缺点模板方法模式的应用场景业务场景开源框架中的应用 对比回调和Hook模式关于组合优先于继承 关于设计模式乱用的现象 模板方法模式 简介 模板方法模式是一种行为型设计模式,该设计模式的核心在于通过抽象出一套相对…...
基于SpringBoot的酒店客房管理系统
基于SpringBoot的酒店管理系统、酒店客房管理系统 开发语言:Java数据库:MySQL技术:SpringBoot、Vue、Mybaits Plus、ELementUI工具:IDEA/Ecilpse、Navicat、Maven 系统展示 首页 管理员界面 用户界面 代码展示 <temp…...
消息队列-RabbitMQ(二)
接上文《消息队列-RabbitMQ(一)》 1、RabbitMQ概念...
程序通过命令行获取操作系统名称+版本+CPU名称等:Part2
文章目录 (一)沿用的方法(二)问题和调整(2.1)Windows11的版本号是10.0(2.2)Golang和管道符号(Linux)(2.3)最大内存容量 vs 当前安装内…...
微软最热门的10款前端开源项目!
本文来盘点微软开源的十大前端项目,这些项目在 Github 上获得了超过 45 万 Star! Visual Studio Code Visual Studio Code 是一款由微软开发的开源的代码编辑器。它支持多种编程语言,如C、C、C#、Python、JavaScript 和 TypeScript 等&…...
wordpress 用户密码的加密算法/域名注册价格及续费
题意 你有一个长度为n(2≤n≤2∗104)n(2 \le n \le 2*10^4)n(2≤n≤2∗104)的二进制01串01串01串 你需要找到不相交的两个长度至少为⌊n2⌋⌊\frac{n}{2}⌋⌊2n⌋的二进制串使得它们互为倍数关系(也可以相等) 思路 若能在[n/21,n][n/21,n][n/21,n]…...
网站设置首页连接分类页的视频教程/网络营销专业培训学校
在mongo db4.x 中,或mongo db cluser中,如果admin密码忘记了,必须按下面的步骤来做。 思路为注释掉security认证部分,重启mongo server, 重建admin用户,再打开security,重启mongo server,就OK了 on master and slave …...
河南省住房城乡和建设厅网站首页/今日头条关键词工具
求转置矩阵问题 时间限制:3000 ms | 内存限制:65535 KB难度:2描述求一个三行三列的转置矩阵。输入第一行一个整数n<20,表示有n组测试数据,下面是n组数据;每组测试数据是九个整型数(每个数都不大于1000…...
软件系统网站建设/企业网站注册域名的步骤
2021.03.16(二) -兔小灰,我喜欢上你了,怎么办? -喜欢下去。 (啊这) 就算不能找到幸福,我也已经找到你了。 虽然喜欢不能当胡萝卜吃,但如果是和喜欢的兔子一起的话,胡萝卜一定会变…...
建立门派/抖音seo什么意思
Android右滑返回上一个界面的实现方法public class BaseActivity extends Activity implements OnTouchListener {public ProgressDialog progressDialog;public String states;public RequestQueue mQueue;/** 触摸时按下的点 **/PointF downP new PointF();/** 触摸时当前的…...
阿德莱德做网站/单页网站怎么优化
在做条形码识别的时候,有可能碰到条形码因为被破坏,无法识别的情况。通常1D条形码的下面都印着对应的数字。这个时候还可以借助下OCR。虽然OCR的成功率可能不高,但是多一种识别方法也是好的。这里分享下如何用Tesseract.js来识别一张1D条形码…...