NIO(一)——缓冲区Buffer
NIO(一)——Buffer
- NIO简介
- NIO即New IO,是用来代替标准IO的,提供了与标准IO完全不同传输方式。
- 核心:通道(Channel)和缓冲区(Buffer)和选择器(Selectors),Channel负责传输,Buffer负责存储
- 与标准IO的区别
- 标准IO是面向字节流的,NIO是面向缓冲区的
- 标准IO是阻塞IO,NIO是非阻塞IO
- 当线程从通道读取数据到缓冲区时,线程还是可以进行其他事情。当数据被写入到缓冲区时,线程可以继续处理它。从缓冲区写入通道也类似。
NIO具有选择器Selectors
- 选择器用于监听多个通道的事件(比如:连接打开,数据到达)。因此,单个的线程可以监听多个数据通道
- 缓冲区Buffer
- 在Java NIO中负责数据的存取。缓冲区本质上是一块可以写入数据,然后可以从中读取数据的内存。这块内存被包装成NIO Buffer对象,并提供了一组方法,用来方便的访问该块内存。
- 根据数据类型的不同,提供了不同类型的缓冲区(boolean除外):
- ByteBuffer
- ShortBuffer
- IntBuffer
- LongBuffer
- FloatBuffer
- DoubleBuffer
- CharBuffer
- 上述缓冲区的管理方式几乎一致,通过allocate()获取缓冲区:
- ByteBuffer buf = ByteBuffer.allocate(1024);
缓冲区存储数据的两个核心方法:
- put():存数据到缓冲区
- get():从缓冲区取数据
缓冲区中的核心属性:
- capacity:容量,表示缓冲区中最大存储数据的容量,一旦声明不可改变
- limit:界限,表示缓存区冲可以操作数据的大小。limit后的数据不能进行读写(读和写操作含义不同)
- position:位置,表示缓冲区中正在操作的数据的位置
- mark:标记,表示记录当前position的位置,可以通过reset()恢复到mark的位置
- 0<=mark<=position<=limit<=capacity
- 方法:
- flid()方法:在切换读写模式的时候必须调用flid()方法
- buf.flip();
- flip()方法:
public final Buffer flip() {
limit = position;
position = 0;
mark = -1;
return this;
}
- rewind()方法:
- 可重复读数据,将position置0,limit不变
public final Buffer rewind() {
position = 0;
mark = -1;
return this;
}
clear()与compact()方法:
- 一旦读完缓冲区中的数据,需要让缓冲区准备好再次被写入。可以通过clear()或compact方法来完成。
- 如果调用的是clear()方法,position将被置0,limit被设置为capacity的值。即缓冲区被清空。但缓冲区中的数据并未被清除。
- 如果缓冲区中有一些未读的数据,调用clean()方法,数据将“被遗忘”。
- 如果缓冲区中有一些未读的数据,且后续还需要这些数据,但此时想先写些数据,就使用compact()方法。compact()方法将所有未读的数据拷贝到Buffer起始处,然后将position设到最后一个未读元素后面,limit=capacity。
public final Buffer clear() {
position = 0;
limit = capacity;
mark = -1;
return this;
}public abstract ByteBuffer compact();
- 直接缓冲区与非直接缓冲区:
- 非直接缓冲区:通过allocate()方法分配缓冲区,将缓冲区建立在JVM内存中
public static ByteBuffer allocate(int capacity) {
if (capacity < 0)
throw new IllegalArgumentException();
return new HeapByteBuffer(capacity, capacity);
}HeapByteBuffer(int cap, int lim) {
super(-1, 0, lim, cap, new byte[cap], 0);
}ByteBuffer(int mark, int pos, int lim, int cap, byte[] hb, int offset){
super(mark, pos, lim, cap);
this.hb = hb;
this.offset = offset;
}
- 直接缓冲区:
- 通过allocateDirect()方法分配直接缓冲区,将缓冲区建立在物理内存中。可以提高效率
public static ByteBuffer allocateDirect(int capacity) {
return new DirectByteBuffer(capacity);
}DirectByteBuffer(int cap) {
super(-1, 0, cap, cap);
boolean pa = VM.isDirectMemoryPageAligned();
//调用直接内存方法进行分配
int ps = Bits.pageSize();
long size = Math.max(1L, (long)cap + (pa ? ps : 0));
Bits.reserveMemory(size, cap); long base = 0;
try {
base = unsafe.allocateMemory(size);
} catch (OutOfMemoryError x) {
Bits.unreserveMemory(size, cap);
throw x;
}
unsafe.setMemory(base, size, (byte) 0);
if (pa && (base % ps != 0)) {
address = base + ps - (base & (ps - 1));
} else {
address = base;
}
cleaner = Cleaner.create(this, new Deallocator(base, size, cap));
att = null;
}
NIO(一)——缓冲区Buffer的更多相关文章
- NIO之缓冲区(Buffer)的数据存取
缓冲区(Buffer) 一个用于特定基本数据类行的容器.有java.nio包定义的,所有缓冲区都是抽象类Buffer的子类. Java NIO中的Buffer主要用于与NIO通道进行交互,数据是从通道 ...
- nio之缓冲区(Buffer)理解
一.缓冲区简介 Nio中的 Buffer 是用于存储特定基础类型的一个容器.为了能熟练的使用 Nio中的各种 Buffer , 我们需要理解 Buffer 中的 三个重要 的属性. 1. capaci ...
- Java NIO之缓冲区Buffer
Java NIO的核心部件: Buffer Channel Selector Buffer 是一个数组,但具有内部状态.如下4个索引: capacity:总容量 position:下一个要读取/写入的 ...
- Java NIO流 -- 缓冲区(Buffer,ByteBuffer)
用来定义缓冲区的所有类都以Buffer类为基类,Buffer定义了缓冲区的基本特征. 直接子类: ByteBuffer 用来存储byte类型的缓冲区,可以在这种缓冲区中存储任意其他基本类型的二进制值( ...
- Java NIO -- 缓冲区(Buffer)的数据存取
缓冲区(Buffer): 一个用于特定基本数据类型的容器.由 java.nio 包定义的,所有缓冲区都是 Buffer 抽象类的子类.Java NIO 中的 Buffer 主要用于与 NIO 通道进行 ...
- JAVA NIO缓冲区(Buffer)------ByteBuffer常用方法
参考:https://blog.csdn.net/xialong_927/article/details/81044759 缓冲区(Buffer)就是在内存中预留指定大小的存储空间用来对输入/输出(I ...
- NIO(一):Buffer缓冲区
一.NIO与IO: IO: 一般泛指进行input/output操作(读写操作),Java IO其核心是字符流(inputstream/outputstream)和字节流(reader/writer ...
- Java NIO 缓冲区 Buffer
缓冲区 Buffer 是 Java NIO 中一个核心概念,它是一个线性结构,容量有限,存放原始类型数据(boolean 除外)的容器. 1. Buffer 中可以存放的数据类型 java.nio.B ...
- Java-NIO(二):缓冲区(Buffer)的数据存取
缓冲区(Buffer): 一个用于特定基本数据类行的容器.有java.nio包定义的,所有缓冲区都是抽象类Buffer的子类. Java NIO中的Buffer主要用于与NIO通道进行交互,数据是从通 ...
随机推荐
- 3sum(从数组中找出三个数的和为0)
Given an array S of n integers, are there elements a, b, c in S such that a + b + c = 0? Find all un ...
- C++内存分区
C++的内存划分为栈区.堆区.全局区/静态区.字符串常量和代码区. 这里去掉自由存储区,增加了代码区,理由会在下面讲到. 栈区:由系统进行内存的管理. 说明:主要存放函数的参数以及局部变量.栈区由系统 ...
- hadoop配置文件详解系列(二)-hdfs-site.xml篇
上一篇介绍了core-site.xml的配置,本篇继续介绍hdfs-site.xml的配置. 属性名称 属性值 描述 hadoop.hdfs.configuration.version 1 配置文件的 ...
- [译文]Domain Driven Design Reference(一)—— 前言
本书是Eric Evans对他自己写的<领域驱动设计-软件核心复杂性应对之道>的一本字典式的参考书,可用于快速查找<领域驱动设计>中的诸多概念及其简明解释. DDD到目前为止知 ...
- RSAC 2018:人工智能成为驱动网络安全的新 “引擎”
作为全球顶级的权威安全会议,RSA已成为快速了解世界安全趋势的风向标,更是影响安全产业转型与持续发展的重要平台.不同于往年人工智能(AI)在安全领域更多的是一种理论探讨,今年看到的是大量人工智能在安全 ...
- 文本分类学习(六) AdaBoost和SVM
直接从特征提取,跳到了BoostSVM,是因为自己一直在写程序,分析垃圾文本,和思考文本分类用于识别垃圾文本的短处.自己学习文本分类就是为了识别垃圾文本. 中间的博客待自己研究透彻后再补上吧. 因为获 ...
- 架构之微服务(etcd)
1. ETCD是什么 ETCD是用于共享配置和服务发现的分布式,一致性的KV存储系统.该项目目前最新稳定版本为2.3.0. 具体信息请参考[项目首页]和[Github].ETCD是CoreOS公司发起 ...
- 基于DP的矩阵连乘问题
当多个连续可乘矩阵做乘法时,选择正确的做乘顺序可以有效减少做乘法的次数,而选择的方法可以很容易的通过DP实现. 原理就是对于每一个所求矩阵,搜索所有可以相乘得到它的方法,比较它们的消耗,选取最小值作为 ...
- hadoop中setup,cleanup,run和context讲解
hadoop 执行中的setup run cleanup context的作用1.简介1) setup(),此方法被MapReduce框架仅且执行一次,在执行Map任务前,进行相关变量或者资源的集中初 ...
- Effective C++ 读书笔记(1-7)
作者 Scott Meyers 翻译作者 侯捷 C++ 神牛 台湾人 术语: 1.explicit C++提供了关键字explicit,可以阻止不应该允许的经过转换构造函数进行的隐式转换的发生.声明 ...