输入流读取大文件的速度非常慢,为什么



我正在尝试提交一个500 MB的文件。我可以加载它,但我想提高性能。这是慢速代码:

File dest = getDestinationFile(source, destination);
if(dest == null) return false;
in = new BufferedInputStream(new  FileInputStream(source));
out = new BufferedOutputStream(new  FileOutputStream(dest));
byte[] buffer = new byte[1024 * 20];
int i = 0;
// this while loop is very slow
while((i = in.read(buffer)) != -1){
   out.write(buffer, 0, i); //<-- SLOW HERE
   out.flush();
}

我怎么能找到它为什么慢
字节数组大小/缓冲区大小是否足够?你有什么提高表现的想法吗?

提前感谢的任何帮助

您不应该在循环中刷新。您正在使用BufferedOutputStream。这意味着在"缓存"了一定数量的数据后,它会将数据刷新到文件中。您的代码只会在写入少量数据后刷新数据,从而降低性能。

试着这样做:

while((i = in.read(buffer)) != -1){
out.write(buffer, 0, i); <-- SLOW HERE
}
out.flush();

..::编辑:回应以下评论::
在我看来,你根本不应该使用缓冲区。您使用的是缓冲(输出/输入)流,这意味着他们有自己的缓冲区来从磁盘读取数据的"包"并保存数据的"包"。我不能100%确定使用额外缓冲区的性能,但我想让你展示我将如何做到这一点:

File dest = getDestinationFile(source, destination);
if(dest == null) return false;
in = new BufferedInputStream(new  FileInputStream(source));
out = new BufferedOutputStream(new  FileOutputStream(dest));
int i;
while((i = in.read()) != -1){
   out.write(i);
}
out.flush();

在我的版本中,你只会阅读一个BYTE(没有内部)。阅读文档:
http://docs.oracle.com/javase/7/docs/api/java/io/InputStream.html#read()
这个方法返回int,但这只是一个BYTE),但不需要读取整个缓冲区(所以您不需要担心它的大小)。

也许你应该阅读更多关于流的内容,以更好地了解对它们的必要性

最新更新