Java BufferedWriter非常慢 - 300 MB的数据

时间:2015-01-29 10:27:40

标签: java

我正在逐行读取由固定长度记录组成的文本文件,并附加一些值,然后写入另一个文件。

像往常一样,我使用BufferedWriter,发现需要大约20分钟才能读取,附加值并写入另一个文件。

BufferedWriter br = new BufferedReader(new FileReader(infile));
if (br != null) {
    for (String line; (line= br.readLine()) != null;) {
        i= i+ 1;
        line += "    " + String.format("%09d", i) + "S";
        try {
            bw = new BufferedWriter(new FileWriter("out.txt",
                    true));
            bw.write(line);
            bw.newLine();
            bw.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

这是我用过的代码。读取整个文件并附加值仅需7秒,但写入文件似乎很慢。我知道BufferedWriter的速度要慢得多。我没有增加缓冲区大小,因为我逐行阅读,出于同样的原因没有尝试使用nio。

建议我提高速度的方法吗?

3 个答案:

答案 0 :(得分:7)

你在这里至少有两个问题:

  • 您在每次迭代时重新打开输出文件。这几乎一定很慢。在打开阅读器的同时打开它一次。
  • 你没有关闭例外的读者或作者。使用try-with-resources块(Java 7)或try/finally块(Java 7之前版本)

后者不会成为性能问题,但它可能会破坏其他需要关闭文件的代码。

此外,我强烈建议不要使用FileReaderFileWriter,因为两者都使用平台默认编码,而不允许您指定任何其他内容。如果您使用的是Java 7,请使用Files.newBufferedReaderFiles.newBufferedWriter

  • 代码方面较短
  • 默认情况下使用UTF-8(通常是最佳选择)
  • 如果您需要其他内容,可以指定编码

答案 1 :(得分:2)

您正在创建一个新的缓冲区,然后通过它为您处理的每一行输入打开和关闭文件编写器。

相反,在for循环之前创建bw并在之后关闭它。

答案 2 :(得分:0)

有两个原因导致代码运行缓慢:

  1. 每次编写一行时都会创建文件outputstream
  2. 您使用BufferedReader和BufferedWriter逐行读写
  3. 试试这段代码:

    public void copyFile() throws IOException{
        FileInputStream fis = new FileInputStream(new File("in.txt"));
        FileOutputStream fos = new FileOutputStream(new File("out.txt"));
        byte[] buffer = new byte[1024];
        int len;
        while((len = fis.read(buffer)) != -1){
            fos.write(buffer, 0, len);
        }
        fos.close();
        fis.close();
    }
    

    使用FileInputStreamFileOutputStreambuffer,您可以通过增加或减少buffer的大小来控制您的读写速度。