Basic Exception Handling

By | February 28, 2016 | 106 Views

This note will cover as following below:

  1. Overview.
  2. Handle or declare exception.
  3. Create your own exception.
  4. Checked v.s Unchecked Exception.
  5. Throw vs Throws.
  6. Common mistakes.
  7. Advantage of exception.

1. Overview

Figure 1: The Throwable class (source: The Java Tutorials of Oracle).

As can be seen from the Figure 1, an exception object is an instance of a class derived Throwable. The Error hierarchy shows internal errors and resource exhaustion inside Java runtime system. Exceptions that inherit from RuntimeException usually cope with some following problems (your fault because you make a programming error):

  • A bad cast.
  • An outer-bound of array access.
  • A null pointer access.

Exceptions that do not inherit from RuntimeException include:

  • Trying to read past the end of a file position, which means reading from a file in which all data has been read or from an empty file.
  • Trying to open a malformed URL.
  • Trying to find a Class object for a string that does not denote an existing class.

According to Oracle definition, there are three kind of exceptions: Unchecked, Error, and RuntimeException. Following figure below illustrates some things happen when you throw an exception.exception-work

Figure 2: How an exception works in a program.

2. Handle or declare exception

2.1 Handle the exception with appropriate try/catch

Catching Exceptions.

try
{
    some code which may throw an exception of type ExceptionType
}
catch (ExceptionType e)
{
    some code executed if exception e occurred
}

Catching Multiple Exceptions.

try {
    some code which may throw an exception of type ExceptionType1
    or ExceptionType2 or ExceptionType3
}
catch (ExceptionType1 e1) {
    some code executed if exception e1 occurred
}
catch (ExceptionType2 e2) {
    some code executed if exception e2 occurred
}
catch (ExceptionType3 e3) {
    some code executed if exception e3 occurred
}

In Java SE 7 and later, a single catch block can handle more than one type of exception.

...
catch (ExceptionType1 | ExceptionType2 e){
     some code executed if exception type 1 OR exception type 2 occurred.
}

Try/catch with finally: make sure that finally never crashes.

try {
    some code which may throw an exception of type ExceptionType
}
catch (ExceptionType e) {
    some code executed if exception e occurred
}
finally {
    some more code executed in any case
}

2.2 Declare the exception using throws (specify requirement)

class MyAnimation
{ 
    . . .
    // Pass the exception on to the caller
    public Image loadImage(String s) throws EOFException, MalformedURLException
    { 
     . . .
    }
}

One of important thing is that any method might throwing an exception (with the exception of  it’s a subclass of RuntimeException) must declare the exception.

3. Create your own exception

Basically, you are able to create your own exception by extending Exception or one of its sub-type. Your exception will be considered as a checked exception. Thus, the compiler will enforce the handle or declare rule for that exception.

public class TestMyException {

	public static void f() throws MyException {
		System.out.println(" Throwing MyException from f() method");
		throw new MyException();
	}

	public static void g() throws MyException {
		System.out.println(" Throwing MyException from g() method");
		throw new MyException("Originated in g() method");
	}

	public static void main(String[] args) {
		try {
			f();
		} catch (MyException e) {
			e.printStackTrace();
		}
		try {
			g();
		} catch (MyException e) {
			e.printStackTrace();
		}

	}
}

Output in console:

 Throwing MyException from f() method
com.tutorial.exception.MyException
	at com.tutorial.exception.TestMyException.f(TestMyException.java:7)
	at com.tutorial.exception.TestMyException.main(TestMyException.java:17)
 Throwing MyException from g() method
com.tutorial.exception.MyException: Originated in g() method
	at com.tutorial.exception.TestMyException.g(TestMyException.java:12)
	at com.tutorial.exception.TestMyException.main(TestMyException.java:22)

4. Checked v.s Unchecked Exception

Checked exceptions consist of all sub-types of Exception (excluding RuntimeException). Any method might throws a checked exception that must follow either the handle or declare rule. Put it another ways, these exceptions enable programmers to make a  well-written program which catches exceptions and notifies users’ mistakes as well as suitable actions to deal with, being so-called “foresee and recover from”.

Unchecked exceptions are all sub-types of Error and RuntimeException, so the compiler does not enforce the handle or declare rule.

5. Throw v.s Throws

Throw statement Throws clause
Throws some Throwable Object explicitly. Declare an exception.
By using throw keyword you cannot throw more than one exception. Declare multiple exceptions.
Followed by an instance variable. Followed by exception class names.
Used inside method body to invoke an exception. Signature of method.

Table 1: Comparison between Throw and Throws in Java.

Example 1: Throw a sub-type of Throwable Object

/**
*  Returns the tail of the list or throws an exception if the list is empty
*  @thows IllegalStateException if the list is empty
*/
public List tail(){
   if (empty()){
     throw new IllegalStateException(“Trying to access tail of an empty list”);
   }
   return tail;
}

Example 2: Throw a defined exception

/**
* An exception indicating an invalid balance amount
*/
public class InvalidBalanceException extends RuntimeException{
   public InvalidBalanceException(String errorMessage){
      System.out.println(errorMessage);
   }
}

public class CarLoan{
  /**
  * Deposits the specified amount into the account.
  * Print out the warning and does not deposit anything 
  * if the balance would go above 0
  */
  public void deposit( int amount, int day, int year){
       if(getBalance() == 0){
              //set balance and add to transaction
       }else{
             throw new InvalidBalanceException( “Sorry! Cannot deposite”);
       }
  }
}

6. Common mistakes

6.1 Calling method doesn’t handle or declare the checked exception.

void doStuff() {
    doSomethingMore();
}
void doSomethingMore(){
    throw new IOException();
}

The doSomethingMore method throws a checked exception, but does not declare it.

void doSomethingMore() throws IOException{...}

The doStuff method is still in problem because it must declare the IOException, or handles it by using a try/catch, with a catch clause that can that an IOException.

6.2 Do not micromanage exceptions. Many programmers wrap every statement in a separate try block.

OutputStream out;
Stack s;
for (i = 0; i < 100; i++)
{ 
   try{ 
      n = s.pop();
   }catch (EmptyStackException s){
      // stack was empty
   }
   try{ 
      out.writeInt(n);
   }catch (IOException e){
      // problem writing to file
   }
}

// Fixed by following code:
try{ 
   for (i = 0; i < 100; i++)
   { 
      n = s.pop();
      out.writeInt(n);
   }
}catch (IOException e){ 
   // problem writing to file
}catch (EmptyStackException s){
   // stack was empty
}

6.3 You should not advertise internal Java Error or unchecked exceptions inheriting from RuntimeException.

class MyAnimation
{ 
   . . .
   void drawImage(int i) throws ArrayIndexOutOfBoundsException // bad style
   { 
     . . .
   }
}

Because ArrayIndexOutOfBountsException is sub-type of RuntimeException. It should be better to fix them instead of throwing the possibility they can happen.
6.4 Keep the exception being silently ignored.

public Image loadImage(String s)
{ 
try
{ 
   code that threatens to throw checked exceptions
}
catch (Exception e)
{} //  horrible style there
}

6.5 You cannot have a catch or finally without a try.

void doSomething(){
   Cafe c = new Cafe();
   c.order();
   catch(CafeException ex) { } // Illegal where is the try?
}

6.6 You cannot put code between the try and the catch.

try {
    doSomething();
}
int a = 13;   // Illegal 
} catch (Exception ex) { ... }

6.7 A try MUST be followed by either a catch or a finally.

try {
   doSomething();
} finally {
   //Clean up 
}

6.8 A try with only a finally (no catch ) must still declare the exception.

void doSomething () throw CafeException {
   try{
     order(); 
   } finally { }    // A try without a catch does not satisfy the handle or declare rule.
}

7. Advantage of exception

Exceptions allow you to (if nothing else) force the program to stop and tell you what went wrong, or(ideally) force the program to deal with the problem and return to a stable state. (*)

References:

  • Bruce Eckel, “Error Handling with Exception”, in Thinking in Java, pp.313-354, MindView Inc, 4th ed, 2006.
  • Cay S. Horstmann, and Gary Cornell, “Exceptions, Logging, Assertions, and Debugging”, in Core Java. Vol I Fundamental, Chapter 11, pp.552-559, Sun Microsystems Inc., 8th ed, 2008.
  • Kathy Sierra, and Bert Bates, “Risky Behavior: exception handling”, in Head First Java, pp.315-335, O’Reilly 2nd ed.
  • Oracle Inc, “Flow Control, Exception, and Assertion”, in Sun Certified Programmer for Java 6 Exam 310-065, Chapter 5, pp.356-382.
  • “Exceptions”, Oracle Java Document. Accessed Feb 28, 2016, https://docs.oracle.com/javase/tutorial/essential/exceptions/index.html.

 

Leave a Reply

Your email address will not be published. Required fields are marked *