wiki:Skript/2. Java/ 9. Ausnahmebehandlung

Version 5 (modified by rhe, 8 years ago) (diff)

--

Ausnahmen

Im Programmablauf können Ausnahmesituationen auftreten.

– z.B. Division durch Null, Datei nicht vorhanden, Übergabe eines ungültigen Parameters an eine Methode...

– allgemein: Zustand, der das Programm daran hindert, im normalen Ablauf fortzufahren

Ziele des Entwicklers

– Erstellen eines stabilen Programms

– Trennung von fachlichem Code und Fehlerbehandlungscode

Es ist häufig einfacher, Ausnahmesituationen eintreten zu lassen und sie ordentlich zu behandeln, als sie unbedingt zu vermeiden.

Den überwachten Programmbereich (Block) leitet das Schlüsselwort try ein. Dem try-Block folgt in der Regel [In machen Fällen auch ein finally-Block, sodass es dann ein try-finally wird. ] ein catch-Block, in dem Programmcode steht, der den Fehler behandelt. Kurz skizziert, sieht das so aus:

{{{ !java try {

Programmcode, der eine Ausnahme ausführen kann

} catch ( … ) {

Programmcode zum Behandeln der Ausnahme

} Es geht ganz normal weiter, denn die Ausnahme wurde behandelt }}}

Deklarieren und Werfen von Exceptions:

public class Bibliothek {
...
  public int zahlDerNeuerscheinungen(int jahr)
      throws UngueltigesJahrException{
    if(jahr > 1452) {
      ... // in jahr erschienene Bücher zaehlen
    }
    return gefundeneAnzahl; // Wert zurückgeben}
    else{
      throw new UngueltigesJahrException(); // Fehlersignal
    }
  }
...
}

Wenn Exception auftritt, wird die Bearbeitung des try-Blocks abgebrochen und mit catch-Block fortgefahren.

...
try{
  int anzahlNeue = uniBib.zahlDerNeuerscheinungen(suchJahr);
  if(anzahlNeue== 0){
    System.out.println("Keine Buecher gefunden.");
  }
  else{
    System.out.println(anzahlNeue + " Buecher gefunden.");
    System.out.println("Buchliste anzeigen?");
...
  }
}
catch(UngueltigesJahrException e) {
  System.out.println("Ungültiges Suchjahr.");
}
...

Wenn keine Exception auftritt wird der catch-Block übersprungen.

finally-Block

Gelegentlich sind "Aufräumarbeiten" wie das Schließen von Dateien nötig, unabhängig davon, ob eine Exception auftrat oder nicht.

Nach einem (oder mehreren) catch kann optional ein finally-Block folgen. Die Laufzeitumgebung führt die Anweisungen im finally-Block immer aus, egal, ob ein Fehler auftrat oder die Anweisungen im try-catch-Block optimal durchliefen.

try {
    // Berechne ...
} catch (OutOfMemoryError e) {
    // Ein Error ist keine Exception und muss separat abgefangen werden
    e.printStackTrace();
} catch (RuntimeException e) {
    // z. B. IndexOutOfBoundsException, NullPointerException usw.
    System.err.println("Offensichtlich ein Programmierfehler!");
    throw e; // Leite nach oben weiter
} catch (Exception e) {
    // Fange alle restlichen Ausnahmefehler ab
    e.printStackTrace();
} catch (Throwable t) {
    // Das hier fängt wirklich alles ab
    t.printStackTrace();
} finally {
    // Ob Exception oder nicht, führe das hier auf jeden Fall aus
    System.out.println("Berechnung beendet oder abgebrochen");
}