确定InputStream的大小

Chr*_*III 62 java arrays size inputstream

我目前的情况是:我必须读取文件并将内容放入InputStream.之后我需要把它的内容InputStream放到一个字节数组中,这个数组需要(据我所知)的大小InputStream.有任何想法吗?

根据要求,我将显示我从上传文件创建的输入流

InputStream uploadedStream = null;
FileItemFactory factory = new DiskFileItemFactory();
ServletFileUpload upload = new ServletFileUpload(factory);
java.util.List items = upload.parseRequest(request);      
java.util.Iterator iter = items.iterator();

while (iter.hasNext()) {
    FileItem item = (FileItem) iter.next();
    if (!item.isFormField()) {
        uploadedStream = item.getInputStream();
        //CHANGE uploadedStreambyte = item.get()
    }
}
Run Code Online (Sandbox Code Playgroud)

该请求是一个HttpServletRequest对象,它是象FileItemFactoryServletFileUpload是从Apache通用FileUpload包.

W. *_*eed 42

这是一个真正的老线程,但当我搜索问题时,它仍然是第一个弹出的东西.所以我只是想补充一下:

InputStream inputStream = conn.getInputStream();
int length = inputStream.available();
Run Code Online (Sandbox Code Playgroud)

为我工作.而且比这里的其他答案简单得多.

  • 我不认为这是准确的.来自Javadocs:"请注意,虽然InputStream的某些实现将返回流中的总字节数,但许多实际上不会.使用此方法的返回值来分配用于保存此数据的所有数据的缓冲区永远不正确流." 因此它可能适用于您的VM,但可能不适用于其他人.http://docs.oracle.com/javase/7/docs/api/java/io/InputStream.html#available() (73认同)
  • 这是错误的!正如[文档](http://docs.oracle.com/javase/7/docs/api/java/io/InputStream.html#available())所说的`available()`方法"注意,虽然有些InputStream的实现将返回流中的总字节数,许多不会.使用此方法的返回值来分配用于保存此流中所有数据的缓冲区是绝对正确的." (9认同)
  • 当你在ByteArrayInputStream中拥有内存中的所有数据时,这是完美的. (4认同)
  • 哦,心理.好抓!我想这个技巧对于需要可移植的代码并不好.我正在用于学校项目,所以它对我有用.谢谢,很高兴知道未来! (3认同)
  • 答案是误导性的,如何[Android docs](http://developer.android.com/intl/ru/reference/java/io/InputStream.html#available()),有明确说明:"请注意**这种方法提供了这样一种弱保证****它在实践中不是很有用**". (3认同)

Bri*_*new 35

我会读入ByteArrayOutputStream然后调用toByteArray()来获取结果字节数组.您不需要提前定义大小(尽管如果您知道它可能是一个优化.在许多情况下您不会)

  • 如果您想要的只是大小,这真的不是内存效率低下吗? (4认同)
  • 是.你得到完整的原始字节数组,没有转换,没有问题. (2认同)

And*_*ffy 19

如果不读取它,您无法确定流中的数据量; 但是,您可以询问文件的大小:

http://java.sun.com/javase/6/docs/api/java/io/File.html#length()

如果无法做到这一点,您可以将从输入流中读取的字节写入ByteArrayOutputStream,它将根据需要增长.


aka*_*okd 12

我只想补充一点,Apache Commons IO有流支持实用程序来执行复制.(顺便说一下,将文件放入输入流是什么意思?你能告诉我们你的代码吗?)

编辑:

好的,你想对项目的内容做什么?有一个item.get() 返回字节数组中的整个东西.

EDIT2

item.getSize()将返回上传的文件大小.


ams*_*raf 6

对于InputStream

org.apache.commons.io.IoUtils.toByteArray(inputStream).length
Run Code Online (Sandbox Code Playgroud)

对于可选的<MultipartFile>

Stream.of(multipartFile.get()).mapToLong(file->file.getSize()).findFirst().getAsLong()
Run Code Online (Sandbox Code Playgroud)


Sam*_*uel 6

下面的函数应该适用于任何InputStream. 正如其他答案所暗示的那样,如果不通读它,您就无法可靠地找到 an 的长度InputStream,但与其他答案不同,您不应尝试通过读入 a 将整个流保存在内存中ByteArrayOutputStream,也没有任何理由这样做。理想情况下,您应该依赖其他 API 来获取流大小,而不是读取流,例如使用 API 获取文件的大小File

public static int length(InputStream inputStream, int chunkSize) throws IOException {
    byte[] buffer = new byte[chunkSize];
    int chunkBytesRead = 0;
    int length = 0;
    while((chunkBytesRead = inputStream.read(buffer)) != -1) {
        length += chunkBytesRead;
    }
    return length;
}
Run Code Online (Sandbox Code Playgroud)

chunkSize选择适合该类型的合理值InputStream。例如,从磁盘读取,如果 的值太小,效率会很低chunkSize