Chapter 12
|
Modified: |
Chapter 12 discusses defensive programming, exception throwing and handling, error reporting and simple file processing.
exception - an object representing details of a program failure. An exception is thrown to indicate a failure has occured. Java uses exceptions to signal failure, such as division by 0, as in the example below.
public class Div
{public int divide()
{return 123 / 0;
}}
The problem is our program just died! Not an impressive performance but errors do occur.
A more robust approach than dying is to catch exceptions and try to recover gracefully.
Below, we:
- try division
- dividing by zero throws an exception
- catch the exception
Example
Terminal Output public class Example { public int divide() { try { return 123 / 0; } catch(Exception e) { System.out.println("Error!! " + e); } return 0; } }
Error!! java.lang.ArithmeticException: / by zero
The basic exception mechanism consists of four elements:
- throws Exception in the signature states that a method may throw an exception, or not, depending on the circumstances. Division normally does not except when dividing by 0.
- throw new Exception("I am an exception") constructs an Exception with the string "I am an exception" and throws it to the caller.
- try { } defines the statements that may throw an exception. The call to method test() must be in a try {} block because of the throws Exception in the signature.
- catch( Exception e ) is called by throw new Exception("I am an exception") with e="I am an exception".
Example
Terminal Output public class Example { public void start() { System.out.println("1"); try { System.out.println("2"); test(); System.out.println("3"); } catch(Exception e) { System.out.println("4 "+ e); } System.out.println("5"); } private void test() throws Exception { throw new Exception("I am an exception"); } }
1
2
4 java.lang.Exception: I am an exception
5
In the following example, an exception is thrown on attempting division by zero.
Example
Terminal Output public class Example { public void start() { System.out.println("1"); try { System.out.println("2"); System.out.println("3 "+ divide(9, 0) ); } catch(Exception e) { System.out.println("4 "+ e); } System.out.println("5"); } public int divide( int dividend, int divisor) throws Exception { if( divisor == 0) throw new Exception("Dividing by zero"); return dividend / divisor; } }
1
2
4 java.lang.Exception: Dividing by zero
5
We have used special return values to indicate failure.
In the Zuul game, false is returned when no door from the Room exists in the direction.
There are several problems with this approach:
- false can represent a failure or success in the Game.
- No magic value is used by everyone to indicate failure, making it harder to recognize failure indicators in a program.
- The failure can be ignored; goRoom() cannot be forced into action on failure.
Game
Player
private void goRoom(Command command)
{
String direction = command.getSecondWord();
if ( !player.go(direction) ) // No door
System.out.println("There is no door!");
else // Door
System.out.println(player.roomDescription());
}public boolean go(String direction)
{
Room nextRoom = currentRoom.getExit(direction);
if (nextRoom == null) // No door
return false;
else { // Door
currentRoom = nextRoom;
return true;
}
}A better approach is to use exceptions, a formal means of indicating failure with the advantages:
- Impossible to ignore,
- Part of the language, purpose recognized by everyone.
Game
Player
private void goRoom(Command command)
{
String direction = command.getSecondWord();
try {
player.go(direction);
System.out.println(player.roomDescription());
}
catch(Exception ex) {
System.out.println("Exception " + ex);
}
}public void go(String direction) throws Exception
{
Room nextRoom = currentRoom.getExit(direction);
if (nextRoom == null)
throw new Exception("No door");
else
currentRoom = nextRoom;
}
Five keys points of exceptions are illustrated below:
- Line 12 - The go() Player method is defined to throw Exception, means that it contains a throw and any caller of go() must be prepared to handle the exception thrown.
- Line 16 - Where the exception is thrown, no other statements are executed in go().
- Line 4 - The try is required because the go() method throws Exception. If an exception is not thrown, statements following are executed (Line 6). If an exception is thrown, the catch is executed.
- Line 8 - The catch is executed when an execution is thrown, when trying the go() method at Line 5.
- Line 9 - The exception parameter ex has the value defined by the Exception("No door") construction.
Game
Player
- private void goRoom(Command command)
- {
- String direction = command.getSecondWord();
- try {
- player.go(direction);
- System.out.println(player.roomDescription());
- }
- catch(Exception ex) {
- System.out.println("Exception: " + ex);
- }
- }
- public void go(String direction) throws Exception
- {
- Room nextRoom = currentRoom.getExit(direction);
- if (nextRoom == null)
- throw new Exception("No door");
- else
- currentRoom = nextRoom;
- }
Exercise 1 - Exceptions in Zuul Assume you're in a room with north and south exits only, the "library" to the north.
- Trace the lines executed starting at Line 1 given the command go north.
- What is the output?
- Trace the lines executed starting at Line 1 given the command go east.
- What is the output?

assertion - a statement of a fact that should be true for normal program execution. Assert statements serve as checks that the program is behaving as expected.
When the assertion is true, the assert does nothing; when false, the assert causes an error, stopping program execution.
The assert statement is turned on during testing, and off when the program is released for production to users.
The result at right occurs when y is 0.
We will examine reading and writing text to and from a file as a case study of exception handling, such as when a file to be read does not exist.
Reading a file
- BufferedReader input - Declares input as BufferedReader, which can open and read a file one character, one line, etc. at a time.
- input = new BufferedReader(new FileReader("C:/Users/username/bluej/chapter07/zuul-better/Game.java")); - Attempts to open a file and assign the object to input. If the file is not found, an exception is thrown, caught and "File not found" printed.
- input.ready() - True when there is more to read from the file.
- input.readLine() - Reads on line from the file.
import java.io.*;
public class IO {
BufferedReader input;
public IO() {
try {
input = new BufferedReader(new FileReader("C:/Users/username/bluej/chapter07/zuul-better/Game.java"));
}
catch( Exception ex ) { System.out.println("File not found:"+ ex); }
}
public void readFile() {
int line = 0;
try {
while( input.ready() ) {
line++;
System.out.println( line + " " + input.readLine() );
}
}
catch( Exception ex ) { System.out.println("Exception: " + ex); }
}
}
Exercise 2 - File IO
- Create a new project named Ch12.
- Create a new class named, IO. Copy the above, paste, compile, and create an IO object.
- Should "File not found" print in the Terminal window:
- What happened and why?
- Check that C:/Users/username/bluej/chapter07/zuul-better/Game.java actually exists.
- Call the readFile method on the IO object.
- What does the method do?
- Change the path to a file that does not exist, compile and attempt to create a new IO object.
- What happens, where and why?
- Call the readFile method on the IO object.
- What happens, where and why?
Writing a file
The above program will be modified to read one file and write to another, a file copy operation.
import java.io.*;
public class IOcopy {
BufferedReader input;
PrintWriter output;
public IOcopy() {
try {
input = new BufferedReader(new FileReader("C:/Users/username/BlueJ/ch12/IO.java"));
output = new PrintWriter(new FileWriter("C:/Users/username/BlueJ/ch12/CopyOfIO.java"));
}
catch(Exception ex) { System.out.println("File not found:"+ ex); }
}
public void copyFile() {
String line;
try {
while( input.ready() ) {
line = input.readLine();
output.println( line );
System.out.println(line);
}
output.close();
}
catch(Exception ex) { System.out.println("Exception " + ex); }
}
}
Exercise 3 - File IOcopy
- Create a new class named, IOcopy. Copy the above, paste, compile, and create an IOcopy object.
- Should "File not found" print in the Terminal window:
- What happened and why?
- Check that C:/Users/username/BlueJ/ch12/IO.java actually exists.
- Call the copyFile method on the IOcopy object.
- What does the method do?