In welchen Situationen sollte man fangen java.lang.Error
an einer Anwendung?
Wenn java.lang.Error zu fangen?
Fast nie. Fehler sind so konzipiert, Fragen, die Anwendungen in der Regel nichts tun. Die einzige Ausnahme könnte sein, die Präsentation des Fehlers zu handhaben, aber auch gehen, dass vielleicht nicht so abhängig von den Fehlern geplant.
Noch nie. Man kann nie sicher sein , dass die Anwendung in der Lage ist , die nächste Codezeile auszuführen. Wenn Sie eine bekommen OutOfMemoryError
, haben Sie keine Garantie , dass Sie in der Lage sein werden , alles zuverlässig zu tun . Fangen Sie Runtime und überprüft Ausnahmen, aber nie Fehler.
Und es gibt noch ein paar andere Fälle , in denen , wenn Sie einen Fehler zu fangen, Sie haben es erneut auslösen . Zum Beispiel Thread soll nie gefangen wird, kann es dazu führen , großes Problem ist , dass Sie es in einer abgeschlossenen Umgebung zu fangen (zB einen Anwendungsserver.):
Eine Anwendung sollte nur Instanzen dieser Klasse fangen, wenn sie asynchron, nachdem sie beendet aufzuräumen müssen. Wenn Thread durch ein Verfahren gefangen wird, ist es wichtig, dass es erneut ausgelöst werden, so dass der Faden tatsächlich stirbt.

Im Allgemeinen nie. Aber manchmal müssen Sie bestimmte Fehler fangen.
Wenn Sie Framework-ish Code schreiben (3rd-Party-Klassen laden), könnte es klug sein LinkageErrors (keine Klasse def gefunden, unzufrieden Link, unvereinbar Klasse ändern) zu fangen. Ich habe auch einige dumme 3rd-Party-Code werfen sublcasses der Fehler gesehen, so dass Sie diese entweder handhaben müssen.
By the way, ich bin nicht sicher, dass es nicht möglich ist, von OutOfMemory zu erholen.
Sehr selten.
Ich würde sagen, nur auf der obersten Ebene eines Fadens, um eine Nachricht mit dem Grunde für einen Thread Sterben erteilen zu wollen.
Wenn Sie in einem Rahmen sind, die diese Art der Sache für Sie tut, lassen Sie es auf den Rahmen.
Eine Error
Regel sollte nicht gefangen werden , da sie einen anormalen Zustand anzeigt , die niemals auftreten sollte .
Aus der Java - API - Spezifikation für die Error
Klasse:
Eine
Error
ist eine Unterklasse von ,Throwable
dass ernsthafte Probleme gibt , die eine vernünftige Anwendung sollte zu fangen nicht versuchen. Die meisten dieser Fehler sind anormalen Bedingungen. [...]Ein Verfahren ist nicht zu erklären, benötigt in ihren throws-Klausel alle Subklassen von Fehlern, die während der Durchführung des Verfahrens, aber nicht gefangen geworfen werden könnten, da diese Fehler anormale Bedingungen sind, die niemals auftreten sollen.
Wie die Beschreibung erwähnt, ein Error
nur unter Umständen ausgelöst wird, die Chancen stehen gut , wenn eine Error
auftritt, gibt es sehr wenig ist , kann die Anwendung tun, und in einigen Fällen in einem instabilen Zustand die Java Virtual Machine selbst sein kann (wie VirtualMachineError
)
Obwohl eine Error
Unterklasse von ist Throwable
was bedeutet , dass sie von einem aufgefangen werden kann try-catch
Klausel, aber es ist wahrscheinlich nicht wirklich nötig, da die Anwendung in einem anormalen Zustand sein wird , wenn ein Error
von der JVM ausgelöst.
Es gibt auch einen kurzen Abschnitt zu diesem Thema in Abschnitt 11.5 die Ausnahme Hierarchie der Java Language Specification, 2. Auflage .
Sehr, sehr selten.
Ich habe es nur für einen sehr , sehr spezifische Fälle bekannt. Zum Beispiel könnte java.lang.UnsatisfiedLinkError wenn zwei werfen wird Unabhängigkeit Classloader Last gleiche DLL. (Ich bin damit einverstanden , dass ich die JAR zu einem gemeinsamen Klassenlader bewegen soll)
Aber häufigste Fall ist, dass Sie um Anmeldung erforderlich zu wissen, was passiert, wenn der Benutzer kommen zu beschweren. Sie möchten eine Nachricht oder ein Popup zu Benutzer, anstatt still tot.
Auch Programmierer in C / C ++, pop sie einen Fehler und sagen etwas, das Menschen nicht verstehen, bevor sie den Ausgang (zB Speicherfehler).
Wenn Sie verrückt genug sind, um einen neuen Unit-Test-Framework zu erstellen, werden Ihre Testläufer wahrscheinlich müssen java.lang.AssertionError von irgendwelchen Testfällen geworfen zu fangen.
Ansonsten siehe andere Antworten.
Generell sollten Sie immer fangen java.lang.Error
und schreiben Sie es in ein Protokoll oder zeigen Sie es an den Benutzer. Ich arbeite in der Unterstützung und sehe täglich , dass Programmierer können nicht sagen , was in einem Programm passiert ist.
Wenn Sie einen Daemon-Thread haben, dann müssen Sie verhindern, dass es beendet wird. In anderen Fällen wird die Anwendung korrekt funktionieren.
Sie sollten nur dann fangen java.lang.Error
auf höchstem Niveau.
Wenn man sich die Liste der Fehler betrachten , werden Sie sehen , dass die meisten gehandhabt werden kann. Zum Beispiel eines ZipError
tritt beim Lesen korrupte Zip - Dateien.
Die häufigsten Fehler sind OutOfMemoryError
und NoClassDefFoundError
, die beide in den meisten Fällen Laufzeitproblemen.
Beispielsweise:
int length = Integer.parseInt(xyz);
byte[] buffer = new byte[length];
produzieren ein kann , OutOfMemoryError
aber es ist ein Laufzeitproblem und kein Grund , das Programm zu beenden.
NoClassDefFoundError
treten meist, wenn eine Bibliothek nicht vorhanden ist oder wenn Sie mit einer anderen Java-Version arbeiten. Wenn es ein optionaler Bestandteil des Programms ist, dann sollten Sie Ihr Programm nicht beenden.
Ich kann viele weitere Beispiele nennen , warum es eine gute Idee zu fangen Throwable
auf der obersten Ebene und eine hilfreiche Fehlermeldung zu erzeugen.
In Multi-Thread-Umgebung, die Sie am häufigsten wollen, es zu fangen! Wenn Sie es zu fangen, melden Sie es, und ganze Anwendung beenden! Wenn Sie das nicht tun, einige Faden, der wäre tot könnten einige entscheidende Teil tun, und der Rest der Anwendung wird denken, dass alles normal ist. Aus, dass können viele unerwünschte Situationen passieren. Ein kleinstes Problem ist, dass man nicht so leicht wäre in der Lage zu Wurzel des Problems zu finden, wenn andere Threads beginnen, einige Ausnahmen zu werfen, weil ein Thread nicht funktioniert.
Zum Beispiel sollte in der Regel Schleife sein:
try {
while (shouldRun()) {
doSomething();
}
}
catch (Throwable t) {
log(t);
stop();
System.exit(1);
}
Auch in einigen Fällen würden Sie verschiedene Fehler anders behandeln wollen, beispielsweise auf OutOfMemoryError Sie Anwendung zu schließen regelmäßig der Lage wäre (vielleicht sogar etwas Speicher frei, und weiter), auf einige andere, gibt es nicht viel Sie tun können.
im Idealfall sollten wir nie Fehler in unserer Java-Anwendung fangen, da es ein unnormaler Zustand ist. Die Anwendung würde in abnormalem Zustand sein und in carshing oder gibt etwas ernsthaft falsch Ergebnis führen könnte.
Es könnte sinnvoll sein, Fehler in Unit-Tests zu fangen, die eine Behauptung wird überprüft. Wenn jemand Behauptungen deaktiviert oder auf andere Weise löscht die Behauptung würden Sie wissen wollen,
In einer Android - Anwendung bin ich fange einen java.lang.VerifyError . Eine Bibliothek , die ich verwende werden Geräte mit einer alten Version des Betriebssystems nicht arbeiten und der Bibliothek Code wird einen solchen Fehler werfen. Ich kann den Fehler natürlich vermeiden , indem Sie die Version von OS zur Laufzeit überprüft, aber:
- Die älteste unterstützte SDK kann für die spezifische Bibliothek in Zukunft ändern
- Der Try-Catch-Fehlerblock ist Teil eines größeren Zurückfallen-Mechanismus. Einige spezielle Geräte, obwohl sie eigentlich die Bibliothek unterstützen, werfen Ausnahmen. Ich fange VerifyError und alle Ausnahmen eine Fallback-Lösung zu verwenden.
Es ist ein Fehler, wenn die JVM nicht mehr wie erwartet funktioniert, oder steht kurz davor, zu. Wenn Sie einen Fehler zu fangen, gibt es keine Garantie, dass der Fang Block läuft, und noch weniger, dass es bis zum Ende laufen wird.
Es hängt auch von dem Laufcomputer, der aktuellen Speicherzustand, so gibt es keine Möglichkeit zu testen, versuchen Sie und Ihr Bestes zu tun. Sie werden nur ein sporadisches Ergebnis.
Sie werden auch die Lesbarkeit des Codes degradieren.
es ist recht praktisch java.lang.AssertionError in einer Testumgebung zu fangen ...
Im Idealfall sollten wir nicht umgehen / catch Fehler. Aber es kann Fälle geben , in denen wir tun müssen, basierend auf Anforderung von Rahmen oder Anwendung. Sagen , dass ich einen XML - Parser - Daemon haben , die implementiert DOM - Parser , die mehr Speicher verbraucht. Wenn es eine Anforderung wie Parser - Thread ist nicht gestorben, wenn es bekommt OutOfMemoryError , stattdessen sollte es damit umgehen und eine Nachricht / Mail an Administrator von application / Rahmen senden.