在Java中使用ByteBuffer有什么用?

什么是Java中的ByteBuffer示例应用程序? 请列出使用这个的任何示例场景。 谢谢!

这是对其用途和缺点的很好的描述。 只要你需要做快速的低级I / O,你就可以使用它。 如果你要实现一个TCP / IP协议,或者你正在编写一个数据库(DBMS),这个类将派上用场。

ByteBuffer类非常重要,因为它构成了在Java中使用通道的基础。 ByteBuffer类在字节缓冲区中定义了六类操作:

  • 绝对和相对的读写单字节的方法;

  • 相对批量获取方法,将连续的字节序列从此缓冲区转移到数组中;

  • 将连续字节序列从字节数组或其他字节缓冲区传输到此缓冲区的相对批量放置方法;

  • 绝对和相对的获取和放置方法,读写其他基本types的值,将它们按特定的字节顺序转换为字节序列或从字节序列转换;

  • 用于创build视图缓冲区的方法,它允许将字节缓冲区视为包含其他基本types值的缓冲区; 和

  • 压缩 , 复制和分割字节缓冲区的方法。

Example code : Putting Bytes into a buffer.

  // Create an empty ByteBuffer with a 10 byte capacity ByteBuffer bbuf = ByteBuffer.allocate(10); // Get the buffer's capacity int capacity = bbuf.capacity(); // 10 // Use the absolute put(int, byte). // This method does not affect the position. bbuf.put(0, (byte)0xFF); // position=0 // Set the position bbuf.position(5); // Use the relative put(byte) bbuf.put((byte)0xFF); // Get the new position int pos = bbuf.position(); // 6 // Get remaining byte count int rem = bbuf.remaining(); // 4 // Set the limit bbuf.limit(7); // remaining=1 // This convenience method sets the position to 0 bbuf.rewind(); // remaining=7 

在Android中,您可以在C ++和Java之间创build共享缓冲区(使用directAlloc方法),并在两侧进行操作。

使用面向stream的API的JAVA IO是使用缓冲区作为用户空间内数据的临时存储来执行的。 通过DMA从磁盘读取的数据首先被复制到内核空间的缓冲区中,然后传送到用户空间的缓冲区。 因此有开销。 避免它可以在性能上取得相当大的收益。

如果有直接访问内核空间中的缓冲区的方法,我们可以跳过用户空间中的这个临时缓冲区。 JAVA NIO提供了这样做的方法。

ByteBuffer是由JAVA NIO提供的几个缓冲区之一。 它只是一个容器或容器来读取数据或写入数据。 上述行为是通过在Buffer上使用allocateDirect()API分配直接缓冲区来实现的。

字节缓冲区的Java文档有有用的信息。

这里有一篇很好的文章解释ByteBuffer的好处。 以下是文章中的要点:

  • 无论是直接还是间接,ByteBuffer的第一个优点是对结构化二进制数据(例如,其中一个答案中所述的低级IO)进行有效的随机访问 。 在Java 1.4之前,要读取这样的数据,可以使用DataInputStream,但不能随机访问。

以下是直接使用ByteBuffer / MappedByteBuffer的好处。 请注意,直接缓冲区是在堆的外部创build的:

  1. 不受gc循环的影响 :直接缓冲区在垃圾回收循环期间不会被移动,因为它们驻留在堆之外。 TerraCota的BigMemorycaching技术似乎非常依赖这个优势。 如果他们堆在一起,会减慢GC停顿时间。

  2. 性能提升 :在数据streamIO中,读取调用将需要系统调用,这需要在用户到内核模式之间进行上下文切换,反之亦然,这将是昂贵的,特别是如果文件被不断地访问。 但是,使用内存映射时,这种上下文切换会减less,因为在内存(MappedByteBuffer)中可能更容易find数据。 如果数据在内存中可用,则直接访问而不调用操作系统,即不进行上下文切换。

请注意,MappedByteBuffers非常有用,特别是如果文件很大并且更less访问频繁的块组。

  1. 页面共享 :内存映射文件可以在进程的虚拟内存空间中分配进程之间共享,并且可以跨进程共享。