Fehlerbehandlung in C++: try/catch von A bis Z – vollständiger Leitfaden

Online Python-Trainer für Anfänger

Lernen Sie Python einfach ohne theoretische Überlastung. Lösen Sie praktische Aufgaben mit automatischer Überprüfung und schreiben Sie Code direkt im Browser.

Kurs starten

Einleitung: Warum Fehlerbehandlung das Fundament zuverlässigen C++-Codes ist



Jedes Programm, das mit der Außenwelt interagiert (Dateien, Netzwerk, Benutzereingaben), stößt unweigerlich auf Ausnahmesituationen. In C++ ist der try/catch-Mechanismus das wichtigste Werkzeug für eine elegante und kontrollierte Handhabung solcher Situationen. In diesem Artikel analysieren wir die Fehlerbehandlung in C++ von den grundlegenden Konstrukten bis hin zu fortgeschrittenen Techniken, einschließlich Best Practices und Fallstricken.



1. Grundlagen: try, catch und throw



Der Ausnahmemechanismus in C++ basiert auf drei Schlüsselwörtern: try, catch und throw.



1.1. try- und catch-Blöcke

Der try-Block enthält Code, der eine Ausnahme auslösen kann. Der catch-Block fängt diese Ausnahme ab und behandelt sie.



#include <iostream>#include <stdexcept>

int main() { try { // Code, der einen Fehler verursachen kann int age = -5; if (age < 0) { throw std::invalid_argument("Alter kann nicht negativ sein"); } std::cout << "Alter: " << age << std::endl; } catch (const std::invalid_argument& e) { std::cerr << "Fehler: " << e.what() << std::endl; } return 0;}


1.2. Ausnahmetypen

In C++ können Ausnahmen jeden Typs ausgelöst werden: Zahlen, Zeichenketten, Klassenobjekte. Es wird jedoch empfohlen, die Standard-Ausnahmeklassen aus <stdexcept> zu verwenden oder eigene Klassen zu erstellen, die von std::exception abgeleitet sind.



  • Standard-Ausnahmen: std::runtime_error, std::logic_error, std::out_of_range usw.
  • Benutzerdefinierte Ausnahmen: werden durch Vererbung von std::exception erstellt.


class MyException : public std::exception {public:    const char* what() const noexcept override {        return "Meine eigene Ausnahme";    }};


1.3. Mehrere catch-Blöcke

Sie können verschiedene Ausnahmetypen in separaten catch-Blöcken abfangen. Die Reihenfolge ist wichtig: spezifischere Ausnahmen sollten zuerst kommen.



try {    // Code} catch (const std::invalid_argument& e) {    // Behandlung von invalid_argument} catch (const std::exception& e) {    // Behandlung aller anderen Ausnahmen aus std} catch (...) {    // catch-all: fängt alles, was oben nicht gefangen wurde}


2. Fortgeschrittene Techniken: Stack-Unwinding und RAII



2.1. Stack-Unwinding

Wenn eine Ausnahme ausgelöst wird, zerstört C++ automatisch alle lokalen Objekte auf dem Weg vom throw-Punkt zum entsprechenden catch. Dieser Vorgang wird als Stack-Unwinding bezeichnet. Er garantiert den Aufruf der Destruktoren für alle Objekte, die in try-Blöcken erstellt wurden.



class Resource {public:    Resource() { std::cout << "Ressource erstellt"; }    ~Resource() { std::cout << "Ressource zerstoert"; }};

void riskyFunction() { Resource res; throw std::runtime_error("Etwas ist schiefgelaufen");}

int main() { try { riskyFunction(); } catch (const std::exception& e) { std::cerr << e.what() << std::endl; } // Ausgabe: Ressource erstellt -> Ressource zerstoert -> Etwas ist schiefgelaufen}


2.2. RAII (Resource Acquisition Is Initialization)

RAII ist eine zentrale C++-Idiom, die eng mit der Fehlerbehandlung verbunden ist. Die Idee: Die Verwaltung von Ressourcen (Speicher, Dateien, Mutexe) wird an die Lebensdauer eines Objekts gebunden. Der Destruktor gibt die Ressource automatisch frei, auch bei einer Ausnahme.



  • Smart Pointer: std::unique_ptr, std::shared_ptr

Blogs

Buchempfehlungen