Write a large text file with NIO

1.8k views Asked by At

I write a large, approximately 1200 (+/- 200) mb , csv file for an offline report in my application. (A thread performs this job.) The data count may run around 50 million, so the query is run for every 50k rows. The query loop runs till empty fetch (for the given criteria). To write the data to the file, instead of using the Java streams, I tried the nio. It took me ~12 seconds to write a huge string with 50000 lines. The same code tried with BufferedWriter took around ~18-22 seconds. The nio approach code is given below. I want to know if this is the straight forward way to use the nio in writing a huge file? Anything I have overlooked, missed? Any other way, optimization and code improvement is welcome.

private static void writeData(FileChannel channel, String data) {
    ByteBuffer buffer = null;
    try {
        buffer = Charset.forName("UTF-8").encode(
                CharBuffer.wrap(data.toCharArray()));
        channel.write(buffer);
    } catch (Exception e) {
        e.printStackTrace();
    }
}
private String writeReport() {
    try {
        FileOutputStream out = new FileOutputStream(pathToFile, true);
        FileChannel channel = out.getChannel();
        // db query
        while(iterate resultset) {
             // get row result
            writeData(channel, data);
        }
    } catch(Exception e){
      //log
    } finally {
      channel.close();
      out .close();
    }
}

//pseudo code with bufferedwriter
private String writeReport(Resultset rs, String file) {
    try {
        BufferedWriter writer = new BufferedWriter(new FileWriter(file), 1024 * 10);
        int headerCount = 0;
        while(rs.next()) {
            String col1 = rs.getString(1);
            String col2 = rs.getString(2);
            String col3 = rs.getString(3);
            String col4 = rs.getString(4);
            String col5 = rs.getString(5);
            String colN= rs.getString(n); //nth column
            if(headerCount==0) {
                writeHeader(writer);
                headerCount++;
            }
            if(col1.equals(condition1)) {
                 writer.append(col1).append(",");
            }
            ......
            if(colN.equals(conditionN)) {
                 writer.append(colN).append(",").append(newLine());
            }
        }
    } catch(Exception e){
      //log
    } finally {
      writer.close();
    }
}
1

There are 1 answers

10
user207421 On

The fastest way to write your file would probably be with a BufferedWriter. If that was slow I would want to see your code. NIO shouldn't be expected to deliver anything startling here, and the code you posted certainly won't be faster than a BufferedWriter, as it will do many more physical writes.