如何提高在Java中读取大文件的速度?

时间:2013-08-08 15:36:59

标签: java java-io

我刚读了一个大小为167MB且行号为1884000的文件。我使用的方法是BufferedReader以获得在线读取它的效果。

我注意到,随着当前行号的增加,读取文件的过程越来越慢(在这种情况下,我花了 3h30min 来完成它)。

我知道使用nio可能会加快这个过程,但我想在线读取文件。

我的代码如下;有人能给我一些建议吗?非常感谢!

String htmlContentPath = html.getAbsolutePath();
BufferedReader reader = new  BufferedReader(new InputStreamReader(new FileInputStream(htmlContentPath)));
String line = null;
int cnt = 0;
while((line = reader.readLine()) != null)       {
    this.proc(line);
    if((cnt++ % 2000) == 0) {
        logger.info("current line number:\t"+cnt);
    }
}

4 个答案:

答案 0 :(得分:2)

你应该可以在这里找到答案:

http://nadeausoftware.com/articles/2008/02/java_tip_how_read_files_quickly

要获得最佳的Java读取性能,需要记住四件事:

  • 通过一次读取数组来最小化I / O操作,而不是一次读取一个字节。一个8K字节的阵列是一个很好的大小。

  • 通过一次获取数据数组来最小化方法调用,而不是一次获取一个字节。使用数组索引来获取数组中的字节数。

  • 如果您不需要线程安全,请最小化线程同步锁。对线程安全类进行较少的方法调用,或者使用非线程安全的类,如FileChannel和MappedByteBuffer。

  • 最大限度地减少JVM / OS,内部缓冲区和应用程序阵列之间的数据复制。将FileChannel与内存映射一起使用,或使用直接或包装的数组ByteBuffer。

答案 1 :(得分:0)

这可能是由交换引起的,取决于proc方法中文件的内存占用,你可以在进程上执行visualVM来查看堆状态,然后调高(xms,xmx)/减少内存消耗你的方法。

干杯。

答案 2 :(得分:0)

当我第一次阅读你的问题时,我建议你注释掉proc()的调用,然后使用其他一些答案来加速文件的读取(这应该是整个执行时间因为你评论了处理呼叫)。

进一步思考,我建议你使用一个分析器(没有任何行注释掉)如果你正在使用Eclipse,那么Eclipse Marketplace上有几个JVM分析器,我确信其他IDE中也有集成的配置文件。 。分析器可以向您显示代码中的热点 - 您似乎大部分时间都在哪些地方。这些信息,加上您对程序逻辑的了解,将会产生加速最严重瓶颈的方法。

这是一个具有更好和更好结果的迭代过程。

我还建议您在测试时首先使用更小的样本文件。

答案 3 :(得分:0)

这对我来说听起来像是一个内存问题(由于内存不足,垃圾收集的需求增加,因此经常出现减速)。

您发布的代码看起来不应该随着行号的增加而减慢(假设proc()调用是“干净的”)。

我是第二个克里斯G的建议删除proc()调用,看看当你只是阅读罚款并且没有处理任何行时,减速仍然会发生。

我还想补充一点,你可以尝试使用-Xmx和-Xms标志,让JVM在一开始就能访问更多的内存。

以下是可能相关的问题:Java threads slow down towards the end of processing