Lecture 18: Exceptions. File and Terminal I/O. Serialization (I)
We start with exceptions, then move to file input, which is a likely source of
Then (probably on Thursday) we will discuss file
output, terminal I/O, and perhaps serialization (which is a nifty way of writing whole
objects to files and reading them back in as if they were primitive types).Exception
s.
1. Exceptions
Exceptions provide
Exceptions in Java are objects. All exception types must extend the
Java language class Throwable
or one of its subclasses.
(By convention, new exception types extend Exception
rather than Throwable
). All exceptions you create should
extend Exception
, making them checked exceptions.
Java exceptions are primarily
RuntimeException
and Error
, thereby
creating Here's what's being thrown:tucotuco.cs.indiana.edu% vi One.java
tucotuco.cs.indiana.edu% cat One.java
class One { public static void main(String[] args) { One one = new One(); one.run(); } void run() { int a = 10, b = 0, c; c = a / b; // oops! System.out.println(a + " / " + b + " = " + c); } }
tucotuco.cs.indiana.edu% javac One.java
tucotuco.cs.indiana.edu% java One
java.lang.ArithmeticException: / by zero at One.run(Compiled Code) at One.main(Compiled Code)
tucotuco.cs.indiana.edu%
Here's a longer and session in which we create andjava.lang.Object | +----java.lang.Throwable | +----java.lang.Exception | +----java.lang.RuntimeException | +----java.lang.ArithmeticException
throw
our
own BadArgumentException
:
The lines marked in red are exceptions thrown when our contrived bug kicks in.tucotuco.cs.indiana.edu% vi Two.java
tucotuco.cs.indiana.edu% cat Two.java
class Two { public static void main(String[] args) { System.out.println("The main method started..."); Two two = new Two(); for (int i = -3; i <= 3; i++) { try { int result = two.factorial(i); System.out.println(" Factorial of " + i + " is: " + result); } catch (BadArgumentException e) { System.out.println(" Factorial was called with negative input: " + e.toString()); } } System.out.println("... main method ends."); } int factorial(int n) throws BadArgumentException { if (n < 0) throw new BadArgumentException(n); if (n == 0) return 1; return n * factorial(n - 1); } } class BadArgumentException extends Exception { int arg; BadArgumentException (int arg) { this.arg = arg; } public String toString() { return " " + arg; } }
tucotuco.cs.indiana.edu% ls -l
total 4 -rw-r--r-- 1 dgerman students 220 Mar 20 19:20 One.java -rw-r--r-- 1 dgerman students 848 Mar 20 20:05 Two.java
tucotuco.cs.indiana.edu% javac Two.java
tucotuco.cs.indiana.edu% ls -l
total 10 -rw-r--r-- 1 dgerman students 515 Mar 20 20:07 BadArgumentException.class -rw-r--r-- 1 dgerman students 220 Mar 20 19:20 One.java -rw-r--r-- 1 dgerman students 1087 Mar 20 20:07 Two.class -rw-r--r-- 1 dgerman students 848 Mar 20 20:05 Two.java
tucotuco.cs.indiana.edu% java Two
The main method started... Factorial was called with negative input: -3 Factorial was called with negative input: -2 Factorial was called with negative input: -1 Factorial of 0 is: 1 Factorial of 1 is: 1 Factorial of 2 is: 2 Factorial of 3 is: 6 ... main method ends.
tucotuco.cs.indiana.edu% vi Two.java
tucotuco.cs.indiana.edu% cat Two.java
class Two { public static void main(String[] args) { System.out.println("The main method started..."); Two two = new Two(); for (int i = -3; i <= 3; i++) { try { int result = two.factorial(i); System.out.println(" Factorial of " + i + " is: " + result); } catch (BadArgumentException e) { System.out.println(" Factorial was called with negative input: " + e.toString()); } } System.out.println("... main method ends."); } int factorial(int n) throws BadArgumentException { if (n < 0) throw new BadArgumentException(n); // if (n == 0) return 1; return n * factorial(n - 1); } } class BadArgumentException extends Exception { int arg; BadArgumentException (int arg) { this.arg = arg; } public String toString() { return " " + arg; } }
tucotuco.cs.indiana.edu% javac Two.java
tucotuco.cs.indiana.edu% java Two
The main method started... Factorial was called with negative input: -3 Factorial was called with negative input: -2 Factorial was called with negative input: -1 Factorial was called with negative input: -1 Factorial was called with negative input: -1 Factorial was called with negative input: -1 Factorial was called with negative input: -1 ... main method ends.
tucotuco.cs.indiana.edu%
2. File Input
The basic flow of processing:
There will be four versions ofpublic void buttonClicked(Button buttonObj) { String fileName = nameField.getText(); try { FileInputStream stream = new FileInputStream(fileName); readAndProcessData(stream); stream.close(); } catch (IOException e) { messageBox("Error in opening input file:\n" + e.toString()); } nameField.requestFocus(); nameField.selectAll(); }
readAndProcessData
that we will look at. One that simply confirms that the file has been opened successfully.
Another one that reads data one character at a time.private void readAndProcessData(FileInputStream stream) { messageBox("Running readAndProcessData\nFile opened successfully"); }
Another one that reads data one line at a time.private void readAndProcessData(FileInputStream stream) { InputStreamReader reader = new InputStreamReader(stream); try { output.setText(""); int data = reader.read(); while (data != -1) { char ch = (char)data; ch = Character.toUpperCase(ch); output.append(ch + ""); data = reader.read(); } } catch (IOException e) { messageBox("Error in file input:\n" + e.toString()); } }
And the last one that reads data one word at a time.private void readAndProcessData(FileInputStream stream) { BufferedReader reader = new BufferedReader(new InputStreamReader(stream)); try { output.setText(""); String data = reader.readLine(); while (data != null) { data = data.toUpperCase(); output.append(data + "\n"); data = reader.readLine(); } } catch (IOException e) { messageBox("Error in file input:\n" + e.toString()); } }
private void readAndProcessData(FileInputStream stream) { StreamTokenizer reader = new StreamTokenizer( new BufferedReader( new InputStreamReader(stream))); try { String data = ""; output.setText(data); reader.nextToken(); while (reader.ttype != StreamTokenizer.TT_EOF) { if (reader.ttype == StreamTokenizer.TT_WORD) { data = reader.sval; data += "(" + data + ")"; // data.toUpperCase(); } else if (reader.ttype == StreamTokenizer.TT_NUMBER) data += "(" + reader.nval + ")"; output.append(data + ""); reader.nextToken(); } } catch (IOException e) { messageBox("Error in file input:\n" + e.toString()); } }