我想复制 InputStream 的“开始”(即前 N 个字符),然后将流重置为其开始位置,以便可以重用。
使用mark()和reset()并不适用于所有类型的输入流,所以我想知道是否有一个“通用”开源Java类(即流包装器)可以对任何类型的输入流执行此操作。
另外,制作副本以避免转换错误的最安全方法是什么?
I want to copy the "start" (i.e., first N characters) of an InputStream and then reset the stream to its start, so that it can be reused.
Using mark() and reset() does not work for all types of input streams, so I was wondering if there is a "generic" open source Java class (i.e., a stream wrapper) that can do this for any type of input stream.
Also, what would be the safest way of making the copy to avoid conversion errors?
发布评论
评论(4)
也许您可以将 InputStream 包装在
PushbackInputStream
这样你就可以读取前 N 个字节,然后unread()
它们用于重用流。Maybe you could wrap your InputStream in a
PushbackInputStream
so you could read the first N bytes thenunread()
them for reuse of the stream.看看 apache commons IOUtils 如何复制流 IOUtils#copyLarge()。
您可以使用 populate ab
ByteArrayInputStream
这样的方式。byte[] buffer = new byte[n];
// n 是使用IOUtils#copyLarge()
中的技术开始填充缓冲区的创建 ByteArrayInputStream您之前创建的 code>buffer
以下是
IOUtils#copyLarge()
的代码片段Take a look at how apache commons IOUtils copies stream IOUtils#copyLarge().
You can use populate ab
ByteArrayInputStream
such a way.byte[] buffer = new byte[n];
// n is the size from startIOUtils#copyLarge()
buffer
you created earlierHere is the code snippet to
IOUtils#copyLarge()
当涉及到重用流并且大小并不重要(例如几兆字节)时,获取流的
byte[]
一次,然后重新创建ByteArrayInputStream
对象必要时使用存储的byte[]
一直对我有用。mark()
和reset()
不再有麻烦。When it comes to reusing a stream and size doesn't matter (e.g. a few mega bytes), getting the
byte[]
of the stream once, and then recreatingByteArrayInputStream
objects with the storedbyte[]
when necessary has always worked for me. No more trouble withmark()
andreset()
.经过相当多的实验后,似乎最好的(尽管不完美)方法是使用 InputStream 的 mark() 和 reset() 方法。
如果原始流不支持标记/重置,一个简单的解决方法是将其包装在 BufferedInputStream 中。*
After quite a bit of experimentation, it seems that the best (although imperfect) approach is to use the mark() and reset() methods of the InputStream.
If the original stream does not support marking/resetting, an easy workaround is to wrap it inside a BufferedInputStream.*