【Netty】NIO 缓冲区 ( Buffer ) 组件
文章目录
- I . NIO 三大核心组件 对应关系
- II . 缓冲区 ( Buffer ) 类
- III . 缓冲区 ( Buffer ) 机制
- IV . 缓冲区 ( Buffer ) 机制 示例解析
- V . 缓冲区 ( Buffer ) 提供的方法
- VI . 字节缓冲区 ( ByteBuffer ) 提供的方法
I . NIO 三大核心组件 对应关系
下图是 NIO 三大核心组件 , 选择器 ( Selector ) , 通道 ( Channel ) , 缓冲区 ( Buffer ) , 与 服务器端线程 , 客户端 , 结构图 ;
1 . 解析上图 NIO 核心组件对应关系 :
① 通道 缓冲区 对应 : 每个 通道 ( Channel ) 都对应一个 缓冲区 ( Buffer ) ;
② 选择器 通道 关联方式 : 每个 选择器 ( Selector ) 对应多个 通道 ( Channel ) , 通道 ( Channel ) 是通过注册的方式 , 注册给 选择器 ( Selector ) ;
③ 选择器 线程 对应 : 每个 选择器 ( Selector ) 对应一个线程 ;
④ 线程 通道 对应 : 每个线程 对应多个 通道 ( Channel ) ;
2 . 引申要素分析 :
① BIO 单向流机制 : BIO 中使用 Socket 进行通信时 , 每个流都是 单向 的 , 输入流只能读取数据 , 不能写出数据 ; 输出流只能写出数据 , 不能读取数据 ;
② 缓冲区 ( Buffer ) 本质 : 缓冲区 ( Buffer ) 本质是一个数组 ;
③ 缓冲区 ( Buffer ) 双向机制 : NIO 中的 缓冲区 ( Buffer ) 是 双向 的 , 既可以读取数据 , 又可以写出数据 , 但是注意读写的方向是相反的 , 读取状态 转为 写出状态时 , 需要调用 flip() 方法翻转 缓冲区 ( Buffer ) ;
④ 通道 ( Channel ) 双向机制 : 通道 ( Channel ) 负责读写 缓冲区 ( Buffer ) , 因此 通道 ( Channel ) 也必须是双向的 ;
⑤ 事件 ( Event ) : 事件 ( Event ) 决定 选择器 ( Selector ) 选择哪条 通道 ( Channel ) , 决定线程 为哪个 通道 ( Channel ) 服务 ;
II . 缓冲区 ( Buffer ) 类
Buffer 常用子类 :
- ByteBuffer : 字节 缓冲区 ;
- ShortBuffer : 短整型 缓冲区 ;
- CharBuffer : 字符 缓冲区 ;
- IntBuffer : 整型 缓冲区 ;
- LongBuffer : 长整型 缓冲区 ;
- DoubleBuffer : 双精度浮点型 缓冲区 ;
- FloatBuffer : 单精度浮点型 缓冲区 ;
上述 ByteBuffer 使用频率最高 , 一般情况下 , 传输数据使用 ByteBuffer 进行数据的传输 ;
III . 缓冲区 ( Buffer ) 机制
缓冲区 ( Buffer ) : 缓冲区 ( Buffer ) 是 在内存中开辟出一块内存 , 并提供一组 API 专门用于读写内存中的数据 ;
缓冲区 ( Buffer ) 机制 : 其内部提供了一系列机制 , 如记录当前的操作 ( 读取 / 写出 ) 位置 等实时信息 ;
缓冲区 ( Buffer ) 标志位 :
① mark : 标记 , 用途由开发者自定义 ;
② position : 标识当前数组索引 ;
③ limit : 缓冲区当前的限制大小 , 如果当前的 position 大于 limit 值 , 无法进行读写操作 , 该值可以修改 ;
④ capacity : 缓冲区 ( Buffer ) 容量 , 缓冲区创建时设置 , 无法修改该容量值 ;
mark ≤\leq≤ position ≤\leq≤ limit ≤\leq≤ capacity
IV . 缓冲区 ( Buffer ) 机制 示例解析
解析 缓冲区 ( Buffer ) 机制 , 逐步 Debug 代码 , 及给出每个步骤的示意图 , 解析过程中的 1 . 2 . 3 . 标号与代码中的标号一致 ;
public class BufferDemo {public static void main(String[] args) {//1 . 创建一个存储 Int 类型数据的 Buffer , 可以存储 8 个 Int 数据IntBuffer buffer = IntBuffer.allocate(8);//2 . 设置 只 读写 3 个元素buffer.limit(3);//3 . 向 Buffer 中写入数据for(int i = 0; i < buffer.limit(); i ++){buffer.put(i);}//从 Buffer 中取出数据//4 . 先将 Buffer 翻转一下 , 然后读取 , 读出的数据与存储的数据顺序一样buffer.flip();//5 . 循环读取 buffer 中的 Int 数据, 维护了一个索引 ,//代表当前操作的数据索引 , 即 positionwhile (buffer.hasRemaining()){System.out.println("position " + buffer.position() + " . " + buffer.get());}}
}
1 . 创建 Buffer 缓冲区 : 此时创建了一个空的缓冲区 , 888 个元素默认初始化为 0 , position
为 000 , limit
和 capacity
为 888 ;
2 . 设置 limit 限制 : 只使用 888 个容器中的 333 个 , 如果 position ≥\geq≥ 3 , 读写时报异常 ;
3 . 向 Buffer 中写入数据 :
① 向 Buffer 中写入 000 : 写入后 , position 变为 111 , 第 0 个元素变为 0 ( 看不出来 ) ;
② 向 Buffer 中写入 111 : 写入后 , position 变为 222 , 第 1 个元素变为 1 ;
③ 向 Buffer 中写入 222 : 写入后 , position 变为 333 , 第 2 个元素变为 2 ; 此时 position ≥\geq≥ limit , 如果在读写缓冲区 , 就要崩溃了 , 退出循环 , 执行下面的操作 ;
4 . 翻转操作 : 将当前的 position 333 设置成 limit , 然后将 position 设置成 000 , 清除 mark 值 ( 这里没有 ) ;
5 . 读取 缓冲区 ( Buffer ) 数据 :
① 读取 第 000 个数据 : 读取到 000 , position 变为 111 ;
② 读取 第 111 个数据 : 读取到 111 , position 变为 222 ;
③ 读取 第 111 个数据 : 读取到 222 , position 变为 333 ; 至此 , 程序全部执行完毕 ;
V . 缓冲区 ( Buffer ) 提供的方法
Buffer 是抽象类 , 是所有的 缓冲区类的父类 , 其提供的以下方法 , 在其它 777 个类中都可以使用 ;
与标志位相关方法 :
- int capacity() : 获取缓冲区容量 ;
- int position() : 获取缓冲区当前读取或写出的索引位置 , 每读取 / 写出 一个元素 , 位置都会自增 , 指向下一个将要读取 / 写出的位置 ;
- Buffer position (int newPosition) : 强行设置缓冲区的位置 , 跳转到指定的位置读取或写出数据 ;
- int limit() : 获取缓冲区可操作性限制大小 ;
- Buffer limit(int newLimit) : 设置缓冲区的新的可操作限制大小 ;
- Buffer mark() : 将当前的 position 设置为 mark ;
- Buffer reset() : 将 position 设置成 mark 的位置 ;
缓冲区变换相关方法 :
- Buffer clear() : 清除缓冲区的四大标志位 , 缓冲区的数据保持不变 ;
- Buffer flip() : 翻转操作 , limit 设置成当前 position 值 , position 设置为 0, mark 清除 ;
- Buffer rewind() : 重绕操作 ;
- Buffer remaining() : 获取当前 position 和 limit 的差值 ;
判定相关方法 :
- boolean hasRemaining() : position 和 limit 是否相等 , 之间还有没有元素 ;
- boolean isReadOnly() : 当前缓冲区是否是可读缓冲区 ;
- boolean isDirect() : 该缓冲区是否是直接缓冲区 ;
数组相关 :
- boolean hasArray() : 该缓冲区的底层实现数组是否可以访问 ;
- Object array() : 获取缓冲区的底层数组 ;
- int arrayOffset() : 获取 缓冲区第一个元素在底层数组中的索引 ;
VI . 字节缓冲区 ( ByteBuffer ) 提供的方法
字节缓冲区 ( ByteBuffer ) 是最常用的缓冲区 , 一般在客户端与服务器端交互使用的最多的就是字节缓冲区 ;
ByteBuffer 是 Buffer 的派生类 , 因此上面的 Buffer 中的所有方法都可以在 ByteBuffer 中使用 ;
缓冲区构建相关 API :
- ByteBuffer allocateDirect(int capacity) : 创建直接字节缓冲区 , 并指定缓冲区大小 ;
- ByteBuffer allocate(int capacity) : 创建字节缓冲区 , 并指定缓冲区大小 ;
- ByteBuffer wrap(byte[] array) : 创建字节缓冲区 , 将 byte 数组放入缓冲区中 ;
- ByteBuffer wrap(byte[] array , int offset , int length) : 创建字节缓冲区 , 将 byte 数组 的 第 offset 个元素开始的 length 个元素 放入缓冲区中 ;
【Netty】NIO 缓冲区 ( Buffer ) 组件相关推荐
- 【Netty】NIO 缓冲区 ( Buffer ) 分散 Scattering 与 聚合 Gathering 操作
文章目录 I . 缓冲区 ( Buffer ) 分散 Scattering 与 聚合 Gathering 概念 II . 缓冲区 ( Buffer ) 分散 Scattering 与 聚合 Gathe ...
- 【Netty】NIO 缓冲区 ( Buffer ) ( 缓冲区读写类型 | 只读缓冲区 | 映射字节缓冲区 )
文章目录 I . 缓冲区 ( Buffer ) 存取类型 II . 只读缓冲区 ( ReadOnlyBuffer ) III . 映射字节缓冲区 ( MappedByteBuffer ) I . 缓冲 ...
- JAVA NIO缓冲区(Buffer)------ByteBuffer常用方法详解
缓冲区(Buffer) 缓冲区(Buffer)就是在内存中预留指定大小的存储空间用来对输入/输出(I/O)的数据作临时存储,这部分预留的内存空间就叫做缓冲区: 使用缓冲区有这么两个好处: 1.减少实际 ...
- java 缓冲区中的数据存入缓冲区中_java8中NIO缓冲区(Buffer)的数据存储详解|chu...
java8新特性NIO缓冲区(Buffer)的数据存储. ByteBuffer,CharBuffer,ShortBuffer,IntBuffer,LongBuffer,FloatBuffer, Dou ...
- 【Netty】NIO 简介 ( NIO 模型 | NIO 三大组件 | 选择器 Selector | 通道 Channel | 缓冲区 Buffer | NIO 组件分配 | 缓冲区示例 )
文章目录 I . NIO 模型 II . NIO 三大组件交互流程 III . NIO 缓冲区 IV . NIO 与 BIO 对比 V . NIO 线程分配 VI . 缓冲区 ( Buffer ) 示 ...
- 【Netty】NIO 选择器 ( Selector ) 通道 ( Channel ) 缓冲区 ( Buffer ) 网络通信案例
文章目录 I . NIO 通信 服务器端 流程说明 II . NIO 通信 服务器端代码 III . NIO 通信 客户端 流程说明 IV . NIO 通信 客户端代码 V . NIO 通信 示例运行 ...
- 【Netty】NIO 通道 ( Channel ) 组件
文章目录 I . 通道 ( Channel ) 概念简介 II . 通道 ( Channel ) 常用类 III . 常用的 通道 ( Channel ) 之 套接字通道 ( SocketChanne ...
- Java NIO基础之缓冲区buffer(笔记 day01)
学习笔记,仅供参考,禁止搬运,如有不正确的地方欢迎大家指正,谢谢!!! 一.缓冲区buffer 代码 package com.lihefei.nio.day01; import org.junit. ...
- java buffer nio_Java NIO之Buffer(缓冲区)入门
Java NIO中的缓存区(Buffer)用于和通道(Channel)进行交互.数据是从通道读入缓冲区,从缓冲区写入到通道中的. 缓冲区本质上是一块可以写入数据,然后可以从中读取数据的内存.这块内 ...
最新文章
- git maven 一键部署_Jenkins实现一键部署maven项目
- 哪些深度相机有python接口_python 从深度相机realsense生成pcl点云
- 圆的半径java_css中的圆形边界半径工件
- 虚拟存储器(虚拟内存Vitual Memory)
- Hive的安装-Hive的交互方式
- 旋转数组中的最小元素 java_程序员算法面试题之旋转数组的最小值
- c语言怎么判断文件类型,判断你的文件是否为合法的PE文件和应用类型
- 数据仓库 和挖掘的步骤 - oracle
- 实现机器学习的循序渐进指南IX ——树回归
- g4600黑苹果efi_在黑苹果系统下挂载和打开EFI(ESP)分区
- 提取Flash芯片信息
- 基于KNN的垃圾邮件分类实验
- html li 点图片,html中ul li前面小黑点样式 ul li一些样式
- 零基础学Python课后实战第五章
- Codeforces 1006A
- Thrift 入门教程【转】
- Java进阶之CollectionsSet接口Map接口
- php7.2 webshell,phpStudy后门分析
- 小程序项目:微信小程序美容理发店预约系统app——计算机毕业设计
- Random Walks: A Review of Algorithms and Applications2020翻译