在我的Windows 7 Files.newInputStream上返回sun.nio.ch.ChannelInputStream。当我测试其性能与FileInputStream时,我惊讶地发现FileInputStream更快。
此测试
InputStream in = new FileInputStream("test");
long t0 = System.currentTimeMillis();
byte[] a = new byte[16 * 1024];
for (int n; (n = in.read(a)) != -1;) {
}
System.out.println(System.currentTimeMillis() - t0);
在125毫秒内读取100mb文件。如果我用
替换第一行InputStream in = Files.newInputStream(Paths.get("test"));
我得到320毫秒。
如果Files.newInputStream比FileInputStream有什么优势?
答案 0 :(得分:8)
如果您测试new FileInputStream
秒,您可能只是看到了操作系统缓存启动的影响。 Java对I / O绑定进程造成任何重大差异是不可信的。反过来尝试它,并在更大的数据集上。
答案 1 :(得分:2)
我不想成为buzzkill,但是javadoc并没有说明任何优势,也没有任何我能找到的文档
打开文件,返回输入流以从文件中读取。的的 流不会被缓冲,并且不需要支持该标记 或重置方法。 该流可安全访问多个 并发线程。阅读从文件开头开始。 返回的流是否可异步关闭和/或 可中断是高度文件系统提供程序特定的因此 未标明。
我认为该方法只是一种实用方法,不一定意味着替换或改进FileInputStream
。请注意,并发点可能会解释一些减速。
答案 2 :(得分:0)
每次创建FileInputStream或FileOutputStream时,都在创建一个对象。即使正确并迅速地将其关闭,它也将被放入一个特殊的类别,该类别只有在垃圾收集器执行完整的GC时才会被清除。遗憾的是,由于向后兼容的限制,无法在JDK中立即解决此问题,因为那里可能存在某些代码,其中有人扩展了FileInputStream / FileOutputStream并依靠这些finalize()方法来确保对close()。
https://dzone.com/articles/fileinputstream-fileoutputstream-considered-harmful
答案 3 :(得分:-2)
该文件说
“流不会被缓冲”
这是因为Files.newInputStream(Paths)支持非阻塞IO。
你可以尝试在调试模式下,你可以打开非阻塞输入流并同时修改文件,但是如果你使用FileInputStream,则不能做这样的事情。
FileInputStream将需要“写入锁定”文件,因此它可以缓冲文件内容,提高读取速度。
但是ChannelInputStream不能。它必须保证它正在读取文件的“当前”内容。
以上是我的经验,我没有检查Java doc中的每一点。