前言:
而今同学们对“java缓冲区的大小”可能比较讲究,朋友们都需要剖析一些“java缓冲区的大小”的相关资讯。那么小编同时在网络上收集了一些对于“java缓冲区的大小””的相关文章,希望咱们能喜欢,大家一起来学习一下吧!与NIO通道交互时使用Java NIO缓冲区。 如您所知,数据从通道读入缓冲区,并从缓冲区写入通道。
缓冲区本质上是一块内存,您可以在其中写入数据,然后您可以再次读取数据。 该内存块被封装在一个NIO缓冲区对象中,该对象提供了一组方法,可以更轻松地使用内存块。
基本缓冲区的使用
使用缓冲区读取和写入数据通常遵循以下四个步骤:
1.将数据写入缓冲区
2.调用buffer.flip()
3.从缓冲区读取数据
4.调用buffer.clear()或buffer.compact()
将数据写入缓冲区时,缓冲区会跟踪您写入的数据量。 一旦您需要读取数据,您需要使用flip()方法调用将缓冲区从写入模式切换到读取模式。 在读取模式下,缓冲区可让您读取写入缓冲区的所有数据。
读完所有数据后,您需要清除缓冲区,使其准备好再次写入。 你可以通过两种方式来做到这一点:通过调用clear()或通过调用compact()。 clear()方法清除整个缓冲区。 compact()方法只会清除已读取的数据。 任何未读数据将被移动到缓冲区的开始处,并且数据将在未读数据之后写入缓冲区。
下面是一个简单的Buffer使用示例,其中写入,翻转,读取和清除操作以粗体显示:
RandomAccessFile aFile = new RandomAccessFile("data/nio-data.txt", "rw");FileChannel inChannel = aFile.getChannel();//创建容量为48字节的缓冲区ByteBuffer buf = ByteBuffer.allocate(48);int bytesRead = inChannel.read(buf); //读入缓冲区。while (bytesRead != -1) { buf.flip(); //使缓冲区准备好读取。while(buf.hasRemaining()){System.out.print((char) buf.get()); // 一次读取1个字节} buf.clear(); //使缓冲区准备好写入bytesRead = inChannel.read(buf);}aFile.close();
缓冲容量,位置和限制
缓冲区本质上是一块内存,您可以在其中写入数据,然后您可以再次读取数据。 该内存块被封装在一个NIO缓冲区对象中,该对象提供了一组方法,可以更轻松地使用内存块。
缓冲区有三个你需要熟悉的属性,以便了解缓冲区的工作原理。 这些是:
capacity (容量)
position (位置)
limit (限制)
位置和限制的含义取决于缓冲区是处于读取还是写入模式。 无论缓冲模式如何,容量总是意味着相同。
以下是写入和读取模式下容量,位置和限制的说明。 解释如下图所示。
容量
作为一个内存块,Buffer具有一定的大小,也称为“容量”。 您只能将容量字节,长整数,字符等写入缓冲区。 一旦缓冲区已满,您需要将其清空(读取数据或清除数据),然后才能向其中写入更多数据。
位置
当您将数据写入缓冲区时,您可以在某个位置执行此操作。 最初的位置为0.当一个字节,长字符等被写入缓冲区时,位置会前进到指向缓冲区中的下一个单元以插入数据。 职位可以最大限度地成为能力 - 1。
当你从缓冲区读取数据时,你也可以从给定的位置进行读取。 当您将缓冲区从写入模式翻转到读取模式时,位置将重置为0.当您从缓冲区中读取数据时,您可以从位置读取数据,并且位置会前进到下一个读取位置。
限制
在写入模式下,缓冲区的限制是可以写入缓冲区的数据量的限制。 在写入模式下,限制等于缓冲区的容量。
当将Buffer转换为读取模式时,限制意味着您可以从数据中读取多少数据的限制。 因此,当将Buffer转换为读取模式时,将限制设置为写入模式的写入位置。 换句话说,您可以读取与写入数量相同的字节(限制设置为写入的字节数,由位置标记)。
缓冲区类型
Java NIO附带以下缓冲区类型:
ByteBuffer (字节缓冲区)
MappedByteBuffer (映射字节缓冲区)
CharBuffer (字符缓冲区)
DoubleBuffer (双缓冲区)
FloatBuffer (浮动缓冲区)
IntBuffer (整型缓冲区)
LongBuffer (长缓整型冲区)
ShortBuffer (短整型缓冲区)
如您所见,这些Buffer类型表示不同的数据类型。 换句话说,它们允许您使用char,short,int,long,float或double来处理缓冲区中的字节。
MappedByteBuffer有点特别,并且将在另一篇独立文章中进行重点介绍。
分配一个缓冲区
要获得一个Buffer对象,你必须首先分配它。 每个Buffer类都有一个allocate()方法来做到这一点。 以下是一个显示ByteBuffer分配的示例,容量为48个字节:
ByteBuffer buf = ByteBuffer.allocate(48);
下面是一个分配CharBuffer的例子,其空间为1024个字符:
CharBuffer buf = CharBuffer.allocate(1024);
将数据写入缓冲区
您可以通过两种方式将数据写入缓冲区:
1.将数据从通道写入缓冲区
2.通过缓冲区的put()方法自己将数据写入缓冲区。
以下是一个示例,显示通道如何将数据写入缓冲区:
int bytesRead = inChannel.read(buf); //读入缓冲区。
这是一个通过put()方法将数据写入缓冲区的示例:
buf.put(127);
还有很多其他版本的put()方法,允许您以许多不同的方式将数据写入缓冲区。 例如,写在特定的位置,或者将一个字节数组写入缓冲区。 有关更多详细信息,请参阅具体缓冲区实现的JavaDoc。
flip()
flip()方法将Buffer从写入模式切换到读取模式。 调用flip()会将位置设置回0,并将限制设置到刚刚位置的位置。
换句话说,位置现在标记为读取位置,限制标记有多少个字节,字符等被写入缓冲区 - 可以读取的字节数,字节数等限制。
从缓冲区读取数据
有两种方法可以从缓冲区中读取数据。
1.将数据从缓冲区读入通道。
2.使用其中一个get()方法自己从缓冲区中读取数据。
以下是如何将数据从缓冲区读取到通道的示例:
//从缓冲区读入通道int bytesWritten = inChannel.write(buf);
这是一个使用get()方法从Buffer读取数据的示例:
byte aByte = buf.get();
还有许多其他版本的get()方法,允许您以多种不同方式从Buffer读取数据。 例如,读取特定的位置,或从缓冲区读取一个字节数组。 有关更多详细信息,请参阅具体缓冲区实现的JavaDoc。
rewind()
Buffer.rewind()将位置设置回0,这样您可以重新读取缓冲区中的所有数据。 该限制保持不变,因此仍然标记可以从缓冲区读取多少个元素(字节,字符等)。
clear()和compact()
一旦完成从Buffer中读取数据,您必须使缓冲区准备好再次写入。你可以通过调用clear()或者通过调用compact()来完成。
如果您调用clear(),则该位置将设置回0并限制容量。换句话说,缓冲区被清除。缓冲区中的数据未被清除。只有标记告诉您可以将数据写入缓冲区的位置。
如果在调用clear()时缓冲区中存在未读取的数据,那么数据将被“忘记”,这意味着您不再有任何标记来指示已读取的数据以及未读取的数据。
如果Buffer中仍有未读数据,并且您想稍后阅读它,但需要先写一些内容,请调用compact()而不是clear()。
compact()将所有未读数据复制到缓冲区的开始处。然后它将位置设置在最后一个未读元素之后。极限属性仍然设置为容量,就像clear()一样。现在缓冲区已准备好写入,但不会覆盖未读数据。
mark() and reset()
您可以通过调用Buffer.mark()方法在Buffer中标记给定的位置。 然后您可以通过调用Buffer.reset()方法将位置重置回标记的位置。 这里是一个例子:
buffer.mark();//多次调用buffer.get(),例如 在解析过程中。buffer.reset(); //设置位置回到标记。
equals() and compareTo()
可以使用equals()和compareTo()比较两个缓冲区。
equals()
如果二个缓冲区是equals:
1.它们是相同的类型(byte,char,int等)
2.它们在缓冲区中具有相同数量的剩余字节,字符等。
3.所有剩余的字节,字符等是相等的。
正如你所看到的,equals只比较缓冲区的一部分,而不是它内部的每一个元素。 实际上,它只是比较缓冲区中的其余元素。
compareTo()
compareTo()方法比较两个缓冲区的其余元素(字节,字符等),用于例如 排序例程。 在下列情况下,缓冲区被认为比另一个缓冲区“小”:
1.第一个元素等于另一个缓冲区中的对应元素,小于另一个缓冲区中的元素。
2.所有的元素都是相等的,但第一个缓冲区在第二个缓冲区之前耗尽元素(元素较少)。
标签: #java缓冲区的大小