User Input (half the truth) 18. Java Input/Output e.g. reading a number: int i = In.readInt(); Our class In provides various such methods. Some of those methods have to deal with wrong inputs: User Input/Console Output, File Input and Output (I/O) What happens with readInt() for the following input? "spam" 472 473 User Input (half the truth) User Input (the whole truth) e.g. reading a number using the class Scanner public class Main { public static void main(String[] args) { import java.util.Scanner; public class Main { Out.print("Number: "); public static void main(String[] args) { int i = In.readInt(); Out.print("Number: "); Out.print("Your number: " + i); Scanner input = new Scanner(System.in); } int i = input.nextInt(); Out.print("Your number: " + i); } } It seems not much happens! } What happens for the following input? Number: spam Your number: 0 "spam" 474 475
Console Output User Input (the whole truth) Until now, you knew: Out.print("Hi") oder Out.println("Hi") Number: spam Without our Out class: Exception in thread "main" java.util.InputMismatchException at java.base/java.util.Scanner.throwFor(Scanner.java:939) System.out.print("The answer is: "); at java.base/java.util.Scanner.next(Scanner.java:1594) at java.base/java.util.Scanner.nextInt(Scanner.java:2258) System.out.println(42); at java.base/java.util.Scanner.nextInt(Scanner.java:2212) System.out.println("What was the question?!"); at Main.main(Main.java:7) This leads to the following output: at TestRunner.main(TestRunner.java:330) Oh, we come back to this in the next chapter... The answer is: 42 What was the question?! 476 477 So: User Input/Console Output Reading/Writing Files (line by line) Files can be read byte by byte using the class java.io.FileReader To read entire lines, we use in addition a Reading of input via the input stream System.in java.io.BufferedReader Writing of output via output stream System.out Files can be written byte by byte using the class java.io.FileWriter To read entire lines, we use in addition a java.io.BufferedWriter 478 479
Reading Files (line by line) Reading Files (line by line) We get the following compilation error: import java.io.FileReader; import java.io.BufferedReader; ./Main.java:6: error: unreported exception FileNotFoundException; must be caught or declared to be thrown public class Main { FileReader fr = new FileReader("gedicht.txt"); public static void main(String[] args) { ^ FileReader fr = new FileReader("gedicht.txt"); ./Main.java:9: error: unreported exception IOException; must be BufferedReader bufr = new BufferedReader(fr); caught or declared to be thrown String line; while ((line = bufr.readLine()) != null){ while ((line = bufr.readLine()) != null){ ^ System.out.println(line); 2 errors } It seems we need to understand more about the topic } “Exceptions” } 480 481 19. Errors and Exceptions ... therefore ... Errors, runtime-exceptions, checked-exceptions, exception handling, special case: resources 482 483
Errors and Exceptions in Java Errors Errors happen in the virtual machine of Java and are not repairable . Errors and exceptions interrupt the normal execution of the program abruptly Examples and represent an unplanned event . No more memory available Exceptions are bad, or not? Too high call stack ( → recursion) Java allows to catch such events and deal with it (as opposed to Missing libraries crashing the entire program) Bug in the virtual machine Unhandled errors and exceptions are passed up through the call stack. Hardware error This glass is broken for good 484 485 Exceptions Exception Types Exceptions are triggered by the virtual machine or the program itself and can typically be handled in order to Runtime Exceptions Checked Exceptions re-establish the normal situation Examples Can happen anywhere Must be declared De-reference null Can be handled Must be handled Division by zero Cause: bug in the code Cause: Unlikely but not Read/write errors (on impossible event files) Errors in business logic Clean-up and pour in a new glass 486 487
Example of a Runtime Exception Unhandled Errors and Exceptions 1 import java.util.Scanner; The program crashes and leaves behind a stack trace . In 2 class ReadTest { there, we can see the where the program got interrupted. public static void main(String[] args){ 3 Exception in thread "main" java.util.InputMismatchException int i = readInt("Number"); 4 [...] } 5 at java.util.Scanner.nextInt(Scanner.java:2076) private static int readInt(String prompt){ 6 at ReadTest.readInt(ReadTest.java:9) System.out.print(prompt + ": "); at ReadTest.main(ReadTest.java:4) 7 Scanner input = new Scanner(System.in); 8 return input.nextInt(); ⇒ Forensic investigation based on this information. 9 } 10 11 } Input: Number: asdf 488 489 Exception gets Propagated through Call Unstanding Stack Traces Stack An unsuited input ... Output: Java VM Runtime ✝ ReadTest.main(); Exception in thread "main" java.util.InputMismatchException at java.util.Scanner.throwFor(Scanner.java:864) at java.util.Scanner.next(Scanner.java:1485) ✘ ✘ ReadTest.main int i = readInt("Number"); at java.util.Scanner.nextInt(Scanner.java:2117) at java.util.Scanner.nextInt(Scanner.java:2076) at ReadTest.readInt(ReadTest.java:9) ✘ return input.nextInt(); ✘ ReadTest.readInt at ReadTest.main(ReadTest.java:4) ... in method readInt on line 9 ... ✘ Scanner.nextInt ✘ ... called by method main on line 4. 490 491
Unstanding Stack Traces Runtime Exception: Bug in the Code?! Where is the bug? import java.util.Scanner; 1 class ReadTest { 2 public static void main(String[] args){ private static int readInt(String prompt){ 3 int i = readInt("Number"); 4 System.out.print(prompt + ": "); } 5 Scanner input = new Scanner(System.in); private static int readInt(String prompt){ 6 return input.nextInt(); System.out.print(prompt + ": "); 7 } Scanner input = new Scanner(System.in); 8 return input.nextInt(); 9 } 10 Not guaranteed that the next input is an int } 11 at ReadTest.readInt(ReadTest.java:9) at ReadTest.readInt(ReadTest.java:9) ⇒ The scanner class provides a test for this at ReadTest.main(ReadTest.java:4) at ReadTest.main(ReadTest.java:4) 492 493 First Finding: often no Exceptional Situa- Runtime Exception: Bug Fix! tion Check first! Often, those “exceptional” cases aren’t that unusual, but pretty foreseeable. In those cases no exceptions should be used! private static int readInt(String prompt){ System.out.print(prompt + ": "); Scanner input = new Scanner(System.in); Examples if (input.hasNextInt()){ Wrong credentials when logging in return input.nextInt(); Empty required fields in forms } else { return 0; // or do something else ...?! Unavailable internet resources } Timeouts } Kids are tipping over cups. You get used to it. 494 495
Second Finding: Avoid Exceptions Exception Types Instead of letting a runtime exception happen, actively prevent such a situation to arise. Runtime Exceptions Checked Exceptions Examples Can happen anywhere Must be declared Check user inputs early Can be handled Must be handled Use optional types Cause: bug in the code Cause: Unlikely but not Predict timeout situations impossible event Plan B for unavailable resources Problem solved. 496 497 Example of a Checked Exception Quick Look into Javadoc private static String[] readFile(String filename){ FileReader fr = new FileReader(filename); BufferedReader bufr = new BufferedReader(fr); ... line = bufr.readLine(); ... } Compiler Error: ./Root/Main.java:9: error: unreported exception FileNotFoundException; must be caught FileReader fr = new FileReader(filename); ^ ./Root/Main.java:11: error: unreported exception IOException; must be caught or declared String line = bufr.readLine(); ^ 498 499 2 errors
Why use Checked Exceptions? Handling Exceptions private static String[] readFile(String filename){ try{ The following situations justify checked exception: FileReader fr = new FileReader(filename); Protected BufferedReader bufr = new BufferedReader(fr); Fault is unprobable but not impossibe – and can be fixed scope ... by taking suitable measures at runtime. line = bufr.readLine(); ... The caller of a method with a declared checked exception is } catch (IOException e){ Measures to re-establis the // do some recovery handling forced to deal with it – catch it or pass it up. normal situation } finally { // close resources Gets executed in any case, } at the end, always! } 500 501 Handling Exceptions: Stop Propagation! Finally: Closing Resources In Java, resources must be closed after use at all costs. Java VM Runtime ReadTest.main(); Otherwise, memory won’t get freed. Resources: Files ReadTest.main lines = readFile("dataset.csv"); Data streams UI elements ✔ ReadTest.readFile line = bufr.readLine(); ... Exception caught! ✘ BufferedReader.readLine ✘ 502 503
Try-With-Resources Statement Specific syntax to close resources automatically : private static String[] readFile(String filename){ try ( FileReader fr = new FileReader(filename); BufferedReader bufr = new BufferedReader(fr)) { ... line = bufr.readLine(); ... Resources get } catch (IOException e){ opened here // do some recovery handling } Resources get closed automatically here } 504
Recommend
More recommend