Do I Need to Close() Both Filereader and Bufferedreader

Do I need to close() both FileReader and BufferedReader?

no.

BufferedReader.close()

closes the stream according to javadoc for BufferedReader and InputStreamReader

as well as

FileReader.close()

does.

closing an buffer reader is compulsory

Always close streams. It's a good habit which helps you to avoid some odd behaviour. Calling close() method also calls flush() so you don't have do this manually.

The best place where to close streams is probably in a finally block. If you have it like in your example and an exception occurs before the in.close() line, the stream won't be closed.

And if you have chained streams, you can only close the last one and all before it are closed too. This means br.close() in your example - not in.close();

Example

try {
// do something with streams
} catch (IOException e) {
// process exception - log, wrap into your runtime, whatever you want to...
} finally {
try {
stream.close();
} catch (IOException e) {
// error - log it at least
}
}

Alternatively you can use closeQuietly(java.io.InputStream) in Apache Commons library.

Use try-with-resources or close this BufferedReader in a finally clause

You are not calling br.close() which means risking a resource leak. In order to reliably close the BufferedReader, you have two options:

using a finally block:

public String loader(String FilePath) {
// initialize the reader with null
BufferedReader br = null;
String str = null;
StringBuilder strb = new StringBuilder();

try {
// really initialize it inside the try block
br = new BufferedReader(new FileReader(FilePath));
while ((str = br.readLine()) != null) {
strb.append(str).append("\n");
}
} catch (FileNotFoundException f) {
System.out.println(FilePath + " does not exist");
return null;
} catch (IOException e) {
e.printStackTrace();
} finally {
// this block will be executed in every case, success or caught exception
if (br != null) {
// again, a resource is involved, so try-catch another time
try {
br.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}

return strb.toString();
}

using a try-with-resources statement:

public String loader(String FilePath) {
String str = null;
StringBuilder strb = new StringBuilder();

// the following line means the try block takes care of closing the resource
try (BufferedReader br = new BufferedReader(new FileReader(FilePath))) {
while ((str = br.readLine()) != null) {
strb.append(str).append("\n");
}
} catch (FileNotFoundException f) {
System.out.println(FilePath + " does not exist");
return null;
} catch (IOException e) {
e.printStackTrace();
}

return strb.toString();
}

How does this FileReader get closed?

When you wrap a FileReader (or any Reader) with a BufferedReader, calling .close() on the BufferedReader will close the wrapped/underlying FileReader as well.

This is true of all the standard Reader, Writer, OutputStream, and InputStream classes that can be used as wrappers.

Why i always need to chain FileReader to other readers?

BufferedReader is mainly used because it is more efficient than a FileReader. The difference between the two is that a FileReader is used to read characters from a file whereas BufferedReader wraps around FileReader and uses it to buffer the input (hence the name BufferedReader). This leads to passing FileReader to BufferedReader ending up with a more efficient way of reading.

But as you asked in the question... It is perfectly fine using FileReader as long as you are okay dealing with what it provides as functionality.

Closing a BufferedReader

If you are using java 7 or greater and your code is in try catch resource block, then it is Auto closes.

If in below versions you have to close with close(). For that you have to change your current way of using and get the reference.

BufferedReader & FileReader read() Performance - Large Text File

Using BufferedReader is indeed faster than using just FileReader.

I executed your code on my machine, with the following text file https://norvig.com/big.txt (6MB).

  • The initial result shows roughly the same time. About 17 seconds each.
  • However, this is because System.out.print() is a bottleneck (within the loop). Without print, the result is 4 times faster with BufferedReader. 200ms vs 50ms. (Compare it to 17s before)

In other words, don't use System.out.print() when benchmarking.

Example

An improved benchmark could look like this using StringBuilder.

File file = new File("/Users/Desktop/shakes.txt");
FileReader reader = new FileReader(file);

int ch;
StringBuilder sb = new StringBuilder();
long start = System.currentTimeMillis();
while ((ch = reader.read()) != -1) {
//System.out.print((char) ch);
sb.append((char) ch);
}
long end = System.currentTimeMillis();

System.out.println(sb);

The above code provides the same output but performs much faster. It will accurately show the difference in speed when using a BufferedReader.



Related Topics



Leave a reply



Submit