# Tips for Using Exceptions in Java

There is a certain amount of controversy about the proper use of exceptions. Some programmers believe that all checked exceptions are a nuisance, others can’t seem to throw enough of them. We think that exceptions (even checked exceptions) have their place, and offer you these **tips** for their proper use.

## I. Exception handling is not supposed to replace a simple test.

As an example of this, we wrote some code that tries 10,000,000 times to pop an empty stack. It first does this by finding out whether the stack is empty.


```
if (!stack.isEmpty()) s.pop();
``` 

Next, we force it to pop the stack no matter what and then catch the **EmptyStackException**.


```
try {
   stack.pop();
}  catch (EmptyStackException e) {
}
``` 
On my test laptop, the version that calls **isEmpty** ran in 20 milliseconds. The version that catches the **EmptyStackException** ran in 3640 milliseconds.

As you can see, it took far longer to catch an **exception** than to perform a **simple** **test**. The moral is: **Use exceptions for exceptional circumstances only.**

## II. Do not micromanage exceptions.

Many programmers wrap every statement in a separate **try** block.


```
for (i = 0; i < 100; i++) {
      try {
        this.method1()
      } catch (EmptyStackException e) {
        // problem 1
      }
      try {
        this.method2()
      } catch (IOException e) {
        // problem 2
      }
}
``` 
This approach blows up your code dramatically.  Just wrap the entire task in a **try** block. If any one operation fails, you can then abandon the task.

```
for (i = 0; i < 100; i++) {
      try {
        this.method1()
        this.method2()
      } catch (EmptyStackException e) {
        // problem 1
      } catch (IOException e) {
        // problem 2
      }
}
``` 
This code looks much cleaner. It fulfills one of the promises of exception handling: to **separate normal processing from error handling**.

## III. Make good use of the exception hierarchy.

Don’t just throw a **RuntimeException**. Find an appropriate subclass or create your own.
Don’t just catch **Throwable**. It makes your code hard to read and maintain.

Do not hesitate to turn an exception into another exception that is **more appropriate**. For example, when you parse an **integer** in a file, catch the **NumberFormatException** and turn it into a subclass of **IOException** or **FileInputFormatException** that you declared.

## IV. Throw early, catch late

Some programmers worry about throwing exceptions when they detect errors. Maybe it would be better to return a **dummy value** rather than throw an **exception** when a method is called with invalid parameters? 

For example, should **Stack.pop** return **null**, or throw an exception when a stack is empty? We think it is better to throw an **EmptyStackException** at the point of failure than to have a **NullPointerException** occur at later time.

Many programmers feel compelled to catch all exceptions that are thrown. Often, it is actually better to **propagate the exception instead of catching it**:

Higher-level methods are often better equipped to inform the user of errors or to abandon unsuccessful commands.

(Source: Core Java Volumn I - Fundamentals)








