IOException is a super class of FileNotFoundException. Therefore your catch block for IOException also catches every FileNotFoundException.
You should implement the function as follows:
public static void writeAssignment(ArrayList<String> assignment, String filename) throws FileNotFoundException {
try (FileWriter writer = new FileWriter(filename)) {
for (String str : assignment) {
writer.write(str + "\n");
}
} catch (FileNotFoundException e) {
throw e; // catch and re-throw
} catch (IOException e) {
System.err.print("Something went wrong");
}
}
Answer from JMax on Stack OverflowIOException is a super class of FileNotFoundException. Therefore your catch block for IOException also catches every FileNotFoundException.
You should implement the function as follows:
public static void writeAssignment(ArrayList<String> assignment, String filename) throws FileNotFoundException {
try (FileWriter writer = new FileWriter(filename)) {
for (String str : assignment) {
writer.write(str + "\n");
}
} catch (FileNotFoundException e) {
throw e; // catch and re-throw
} catch (IOException e) {
System.err.print("Something went wrong");
}
}
You can catch Exception instead of IOException
public static void writeAssignment(ArrayList<String> assignment, String filename) throws FileNotFoundException {
try {
FileWriter writer = new FileWriter(filename);
for (String str : assignment) {
writer.write(str + "\n");
}
writer.close();
} catch (Exception e) {
e.printStackTrace();
}
}
From this type coding, you can see/learn the hierarchy of exceptions. If you want to execute your program whether caught exception or not, you can use finally block. Where you will close your writer.
I agree with @cyber-rookie, it is probably best to close resources in a finally block.
Java 7 introduced "try-with-resources" in order to cut down on programming mistakes...
https://docs.oracle.com/javase/tutorial/essential/exceptions/tryResourceClose.html
You can now write...
try (FileWriter writer = new FileWriter("file.txt")) {
writer.write("i am writing");
} catch (IOException e) {
e.printStackTrace();
}
The compiler will add the extra code to close the writer at the end of the block for you
If your are using Java 7, the best approach is to use try with resource. See https://docs.oracle.com/javase/tutorial/essential/exceptions/tryResourceClose.html
try (FileWriter writer = new FileWriter("file.txt")) {
writer.write("i am writing");
}
Your problem is this line:
FileWriter fw = new FileWriter(file2);
Constructing the FileWriter is throwing an IOException, and because it is outside your try-Catch block, it isn't being caught. I suggest you try addding it in the following way:
try(FileWriter fw = new FileWriter(file2); BufferedWriter bw = new BufferedWriter(fw);)
//and then the rest of your try catch block
This turns your try-catch into a try-with-resources block which basically means once the code is block is finished the writers should automatically close
EDIT
If you assign the variables in the try-with-Resources like so:
try(FileWriter fw = new FileWriter(file2); BufferedWriter bw = new BufferedWriter(fw);
FileInputStream fis = new FileInputStream(file); BufferedInputStream bis = new BufferedInputStream(fis);
DataInputStream dis = new DataInputStream(bis)) {
then you can remove all of these:
// dispose all the resources after using them.
fis.close();
bis.close();
dis.close();
bw.flush();
bw.close();
As the try-with-resources can automatically try and close anything within the (at the start to save you trying to do it manually)
You have unhandle exception here,Try implement try-catch for it
FileWriter fw = new FileWriter(file2);
can be changed to
FileWriter fw=null;
try {
fw = new FileWriter(file2);
}catch(IOException e){
e.printStackTrace();
}
and you can put these resource close in finally block of respective try-catch-finally. You will also need to check if not null
// dispose all the resources after using them.
fis.close();
bis.close();
dis.close();
bw.flush();
bw.close();
fw.close();
The variable fr only has scope within the try block. It is out of scope in the finally block. You need to declare it before the try block:
FileReader fr = null;
try {
fr = new FileReader(file);
BufferedReader br = new BufferedReader(fr);
String line = null;
} catch (FileNotFoundException e) {
e.printStackTrace();
} finally {
if (fr != null) {
try {
fr.close();
} catch (IOException e) {
// This is unrecoverable. Just report it and move on
e.printStackTrace();
}
}
}
This is quite a common pattern of code, so it's good to remember it for future similar situations.
Consider throwing IOException from this method - printing track traces isn't very helpful to callers, and you wouldn't need the nested try catch around fr.close()
Now finally block is not needed,
try (FileReader fr = new FileReader(file);
BufferedReader br = new BufferedReader(fr);){
String line = null;
}
} catch(FileNotFoundException fnf) {
fnf.printStackTrace();
}
now automatically close your readers
Note that the following is only applicable for Java 6 and earlier. For Java 7 and later, you should switch to using try-with-resources ... as described in other answers.
If you are trying to catch and report all exceptions at source (in Java 6 or earlier), a better solution is this:
ObjectOutputStream oos = null;
try {
oos = new ObjectOutputStream(new FileOutputStream(file));
oos.writeObject(shapes);
oos.flush();
} catch (FileNotFoundException ex) {
// complain to user
} catch (IOException ex) {
// notify user
} finally {
if (oos != null) {
try {
oos.close();
} catch (IOException ex) {
// ignore ... any significant errors should already have been
// reported via an IOException from the final flush.
}
}
}
Notes:
- The standard Java wrapper streams, readers and writers all propagate
closeandflushto their wrapped streams, etc. So you only need to close or flush the outermost wrapper. - The purpose of flushing explicitly at the end of the try block is so that the (real) handler for
IOExceptiongets to see any write failures1. - When you do a close or flush on an output stream, there is a "once in a blue moon" chance that an exception will be thrown due to disc errors or file system full. You should not squash this exception!.
If you often have to "close a possibly null stream ignoring IOExceptions", then you could write yourself a helper method like this:
public void closeQuietly(Closeable closeable) {
if (closeable != null) {
try {
closeable.close();
} catch (IOException ex) {
// ignore
}
}
}
then you can replace the previous finally block with:
} finally {
closeQuietly(oos);
}
Another answer points out that a closeQuietly method is already available in an Apache Commons library ... if you don't mind adding a dependency to your project for a 10 line method.
But be careful that you only use closeQuietly on streams where IO exceptions really are irrelevant.
UPDATE : closeQuietly is deprecated in version 2.6 of the Apache Commons API. Java 7+ try-with-resources makes it redundant.
On the issue of flush() versus close() that people were asking about in comments:
The standard "filter" and "buffered" output streams and writers have an API contract that states that
close()causes all buffered output to be flushed. You should find that all other (standard) output classes that do output buffering will behave the same way. So, for a standard class it is redundant to callflush()immediately beforeclose().For custom and 3rd-party classes, you need to investigate (e.g. read the javadoc, look at the code), but any
close()method that doesn't flush buffered data is arguably broken.Finally, there is the issue of what
flush()actually does. What the javadoc says is this (forOutputStream...)If the intended destination of this stream is an abstraction provided by the underlying operating system, for example a file, then flushing the stream guarantees only that bytes previously written to the stream are passed to the operating system for writing; it does not guarantee that they are actually written to a physical device such as a disk drive.
So ... if you hope / imagine that calling
flush()guarantees that your data will persist, you are wrong! (If you need to do that kind of thing, look at theFileChannel.forcemethod ...)
Current best practice for try/catch/finally involving objects that are closeable (e.g. Files) is to use Java 7's try-with-resource statement, e.g.:
try (FileReader reader = new FileReader("ex.txt")) {
System.out.println((char)reader.read());
} catch (IOException ioe) {
ioe.printStackTrace();
}
In this case, the FileReader is automatically closed at the end of the try statement, without the need to close it in an explicit finally block. There are a few examples here:
http://ppkwok.blogspot.com/2012/11/java-cafe-2-try-with-resources.html
The official Java description is at:
http://docs.oracle.com/javase/7/docs/technotes/guides/language/try-with-resources.html