Digital said:
Hi, I'm trying to read multiple text lines from a file into a single
String. The approach I am using is to read each line of the file
with BufferedReader.readLine() and appending it to a String,
but this is really slow:
BufferedReader br = new BufferedReader(fr);
String buffer, result;
while ((buffer = br.readLine()) != null) {
result = result + buffer;
On the first pass, "result" has not been initialized.
}
Is there a better, faster way?
Use a StringBuilder or a StringBuffer. The StringBuilder theoretically
should be a little faster, because it does not provide any guarantee of
synchronization. On my system, they are equally fast. In the program
below, each takes ~300ms to process the input file, plus a 50-ms hit to
whichever is tested first. Here's the output of a run on my system:
Using a StringBuilder took 350 ms.
Using a StringBuffer took 301 ms.
^C
OK, so I killed the String test. It was slowing down my machine.
Here's the code:
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.IOException;
import java.io.Reader;
import java.util.Date;
class Main {
static String readWithString(Reader fr)
throws IOException {
BufferedReader br = new BufferedReader(fr);
String buffer, result = "";
while ((buffer = br.readLine()) != null) {
result = result + buffer;
}
return result;
}
static String readWithStringBuffer(Reader fr)
throws IOException {
BufferedReader br = new BufferedReader(fr);
String line;
StringBuffer result = new StringBuffer();
while ((line = br.readLine()) != null) {
result.append(line);
}
return result.toString();
}
static String readWithStringBuilder(Reader fr)
throws IOException {
BufferedReader br = new BufferedReader(fr);
String line;
StringBuilder result = new StringBuilder();
while ((line = br.readLine()) != null) {
result.append(line);
}
return result.toString();
}
public static void main(String[] args)
throws IOException {
/* Using each of several buffer types, record the time taken to
* concatenate all lines from a text file, without newlines.
*
* The sample text file is ~ 3MB, courtesy of Project Gutenberg.
*
http://www.gutenberg.org/
*/
FileReader f = new FileReader("war_and_peace.txt"); // ~3MB
try {
long t = new Date().getTime();
readWithStringBuilder(f);
t = new Date().getTime() - t;
System.out.println(
"Using a StringBuilder took " + t + " ms.");
} finally {
f.close();
}
f = new FileReader("war_and_peace.txt"); // ~3MB.
try {
long t = new Date().getTime();
readWithStringBuffer(f);
t = new Date().getTime() - t;
System.out.println(
"Using a StringBuffer took " + t + " ms.");
} finally {
f.close();
}
f = new FileReader("war_and_peace.txt"); // ~3MB.
try {
long t = new Date().getTime();
readWithString(f);
t = new Date().getTime() - t;
System.out.println(
"Using a String took " + t + " ms.");
} finally {
f.close();
}
}
}