何时使用字节数组和何时字节缓冲区?
字节数组和字节缓冲区有什么区别?
另外,在什么情况下应该比另一个更受欢迎?
[我的用例是用于在Java中开发的Web应用程序]。
ByteBuffer是新的IO包(nio)的一部分,它是为基于文件的数据的快速吞吐量而开发的。 具体而言,Apache是一个非常快速的Web服务器(用C语言编写),因为它从磁盘读取字节,并直接将它们放在networking上,而不用通过各种缓冲区来移动它们。 它通过内存映射文件来完成,Java的早期版本没有。 随着nio的出现,可以用Java编写一个和Apache一样快的Web服务器。 当你想要非常快的文件到networking的吞吐量,那么你想使用内存映射文件和ByteBuffer。
数据库通常使用内存映射文件,但在Java中这种用法很less有效。 在C / C ++中,可以加载大量内存并将其转换为所需的types化数据。 由于Java的安全模型,这通常是不可行的,因为只能转换为某些本地types,而这些转换效率不高。 ByteBuffer在你只是将字节作为普通字节数据处理时效果最好 – 一旦你需要将它们转换为对象,其他的java io类通常执行得更好并且更容易使用。
如果你不处理内存映射文件,那么你并不需要打扰ByteBuffer–通常你会使用字节数组。 如果您正尝试构build一个Web服务器,并以最快的文件为基础的原始字节数据的吞吐量,那么ByteBuffer(特别是MappedByteBuffer)就是您最好的朋友。
实际上有很多方法来处理字节。 我同意挑选最好的一个并不容易:
-
byte[]
-
java.nio.ByteBuffer
-
java.io.ByteArrayOutputStream
(与其他stream组合) -
java.util.BitSet
byte[]
只是一个原始数组,只包含原始数据。 所以,它没有方便的方法来构build或操作内容。
ByteBuffer
更像一个build造者。 它用来创build一个byte[]
。 与数组不同,它有更方便的辅助方法。 (例如append(byte)
方法)。
你可能会说, ByteBuffer
对byte[]
是这样做的, StringBuilder
是为String
。 但是ByteBuffer
类有一个特定的区别/缺点。 就像数组一样, ByteBuffer
具有固定的大小。 所以,当你实例化它时,你必须指定缓冲区的大小。
这就是为什么我经常更喜欢使用ByteArrayOutputStream
的原因之一, 因为它会像ArrayList
一样自动resize 。 (它有一个toByteArray()
方法)。 有时它是实用的,把它包装在一个DataOutputStream
。 好处是你会有一些额外的方便调用(如writeShort(int)
如果你需要写2个字节)。
当您想执行位级操作时, BitSet
会派上用场。 您可以获取/设置个别位,并且具有像xor()
这样的逻辑运算符方法。 ( toByteArray()
方法仅在java 7中引入)
当然,根据您的需要,您可以将它们全部组合起来构build您的byte[]
。