Download the JDK
Search the Tutorials
Hide the TOC
Trail: Essential Classes
Lesson: Exceptions
Section: Catching and Handling Exceptions
Exceptions
What Is an Exception?
The Catch or Specify Requirement
Catching and Handling Exceptions
The try Block
The catch Blocks
The finally Block
Putting It All Together
Specifying the Exceptions Thrown by a Method
How to Throw Exceptions
Chained Exceptions
Creating Exception Classes
Unchecked Exceptions — The Controversy
Advantages of Exceptions
Summary
Questions and Exercises
Home Page > Essential Classes > Exceptions
« Previous • Trail • Next »
The finally Block

> The `finally` block always executes when the `try` block exits. This ensures that the `finally` block is executed even if an unexpected exception occurs. But `finally` is useful for more than just exception handling — it allows the programmer to avoid having cleanup code accidentally bypassed by a `return`, `continue`, or `break`. Putting cleanup code in a `finally` block is always a good practice, even when no exceptions are anticipated.

> The `try` block of the `writeList` method that you've been working with here opens a `PrintWriter`. The program should close that stream before exiting the `writeList` method. This poses a somewhat complicated problem because `writeList`'s `try` block can exit in one of three ways.

> 1. The `new FileWriter` statement fails and throws an `IOException`.
> 2. The `vector.elementAt(i)` statement fails and throws an `ArrayIndexOutOfBoundsException`.
> 3. Everything succeeds and the `try` block exits normally.
> The runtime system always executes the statements within the `finally` block regardless of what happens within the `try` block. So it's the perfect place to perform cleanup.

> The following `finally` block for the `writeList` method cleans up and then closes the `PrintWriter`.

> >     finally {
> >         if (out != null) {
> >             System.out.println("Closing PrintWriter");
> >             out.close();
> >         } else {
> >             System.out.println("PrintWriter not open");
> >         }
> >     }

> In the `writeList` example, you could provide for cleanup without the intervention of a `finally` block. For example, you could put the code to close the `PrintWriter` at the end of the `try` block and again within the exception handler for `ArrayIndexOutOfBoundsException`, as follows.

> >     try {

> >         out.close();       //Don't do this; it duplicates code.

> >     } catch (FileNotFoundException e) {
> >         out.close();       //Don't do this; it duplicates code.
> >         System.err.println("Caught: FileNotFoundException: "
> >                           + e.getMessage());
> >         throw new RuntimeException(e);

> >     } catch (IOException e) {
> >         System.err.println("Caught IOException: "
> >                           + e.getMessage());
> >     }

> However, this duplicates code, thus making the code difficult to read and error-prone should you modify it later. For example, if you add code that can throw a new type of exception to the `try` block, you have to remember to close the `PrintWriter` within the new exception handler.

> > Important: The `finally` block is a key tool for preventing resource leaks. When closing a file or otherwise recovering resources, place the code in a `finally` block to insure that resource is always recovered.

« Previous • Trail • Next »
Previous page: The catch Blocks
Next page: Putting It All Together