我正在为我的项目开发更新程序,我想快速下载文件。 每次更新时,都有一些文件大小不同。所以我认为我不需要缓冲区,或者肯定没有定义。我写的那样:
File file = new File..
InputStream input = new InputStream...
OutputStream output = new OutputStream(..).write(input.read());
这一个完美运行!但是我的朋友对我说; “嘿,我们从jdk7获得了FileChannel”。 我已经考虑过了,但是我们无法创造和将数据导入FileChannel而不使用ByteBuffer。
FileChannel channel = new FileOutputStream(file).getChannel();
ByteBuffer buffer = ByteBuffer.allocateDirect(..);
buffer.putInt(inputstream.read());
channel.write(buffer);
那么什么更快?好吗?谢谢!
更新:(我认为,最快的解决方案)
URLConnection connection = new URL(url).openConnection();
File file = new File(connection.getURL().getPath().substring(1));
if (file.getParentFile() != null)
file.getParentFile().mkdirs();
FileChannel output = new FileOutputStream(file).getChannel();
output.transferFrom(Channels.newChannel(connection.getInputStream()), 0, connection.getContentLengthLong());
有效!
答案 0 :(得分:4)
下载没有缓冲区的文件:Nio比io快?
无论使用传统的I / O流还是NIO API,不太可能对下载时间产生任何影响。
下载速度通常受网络限制。比如:
然后,存在“另一端”是否能够以“网络”能够承载的速率提供(或消费)数据的问题。这通常取决于光盘和网络I / O带宽以及另一端的负载。
一般来说,客户端将数据从内存缓冲区移动到本地目标文件的能力不是问题。
在您(IMO)浪费更多时间之前,我建议您实施下载代码“简单方法”。然后对其进行基准测试/配置(使用实际下载)以确定性能瓶颈是在代码中还是(我怀疑)在“网络”中。只有在您的测量表明它可能值得的时候才能优化您的代码。
更新 - 我刚刚注意到在您的原始版本中,您一次读取一个字节数据(使用来自无缓冲输入流的read()
。这个绝对是效率低下,可能会对下载速度造成影响。如果要以小块(例如一次一个字节)从流中读取(或写入流),那么应该将其包装起来使用相应的缓冲流;例如BufferedInputStream
,BufferedOutputStream
,BufferedReader
,BufferedWriter
。
使用缓冲流与非缓冲流之间的性能差异(对于小型I / O操作)数量级比经典流与NIO之间的差异更重要。