1151 Stimmen

Wie kann ich einen `try`/`except`-Block schreiben, der alle Ausnahmen abfängt?

Wie kann ich eine try / except Block, der alle Ausnahmen abfängt?

6 Stimmen

In den meisten Fällen machen Sie wahrscheinlich etwas falsch, wenn Sie versuchen, eine Ausnahme abzufangen. Ich meine, Sie können einfach etwas in Ihrem Code falsch schreiben und Sie werden es nicht einmal merken. Es ist eine gute Praxis, bestimmte Ausnahmen abzufangen.

38 Stimmen

Um genauer zu sein, ist das Abfangen aller möglichen Ausnahmen nur dann ein Problem, wenn sie unbemerkt abgefangen werden. Es ist schwer vorstellbar, wo dieser Ansatz sonst noch angebracht ist, außer wenn die abgefangenen Fehlermeldungen nach sys.stderr und möglicherweise protokolliert. Das ist eine absolut gültige und übliche Ausnahme.

1 Stimmen

Haben Sie es versucht: try: whatever() except Exception as e: exp_capture() ?

1342voto

Duncan Punkte 85702

Abgesehen von einer bloßen except: Klausel (die Sie, wie andere gesagt haben, nicht verwenden sollten), können Sie einfach die Exception :

import traceback
import logging

try:
    whatever()
except Exception as e:
    logging.error(traceback.format_exc())
    # Logs the error appropriately. 

Normalerweise würden Sie dies nur auf der äußersten Ebene Ihres Codes in Erwägung ziehen, wenn Sie z. B. nicht abgefangene Ausnahmen vor der Beendigung behandeln wollen.

Der Vorteil von except Exception über die kahlen except ist, dass es einige wenige Ausnahmen gibt, die nicht erfasst werden, am offensichtlichsten KeyboardInterrupt y SystemExit : Wenn Sie diese auffangen und verschlucken, können Sie es jedem schwer machen, Ihr Skript zu verlassen.

1 Stimmen

Ich hatte die gleiche Sache in meinem Verstand, aber ihr ist ein Nachteil, nehmen Sie an, ihre sind zwei Fehler, wenn einmal gefangen wird und in außer Sie gerade drucken Sie aus dem Try-Block und Sie werden nie wissen, den zweiten Fehler...

8 Stimmen

Für alle, die sich wundern, ganz im Gegensatz zu meiner Erwartung wird dies noch fangen non-exception subclassing Dinge wie ints, zumindest in Python 2.x.

11 Stimmen

@JosephGarvin, das ist falsch, d.h. es werden keine "Nicht-Ausnahmen" abgefangen, die nicht zur Unterklasse Exception . Beachten Sie, dass es unmöglich ist, eine int als eine Ausnahme, und der Versuch, dies zu tun, führt zu einer TypeError Ausnahme, die von der umschließenden except Exception Klausel in einem solchen Fall. Andererseits kann eine Klasse im alten Stil ausgelöst werden, die sich als "Nicht-Ausnahme" qualifiziert und keine Unterklasse ist Exception - dies wird von einer Nacktschnecke erwischt werden except Klausel aber pas durch eine except Exception Klausel.

762voto

Tim Pietzcker Punkte 311448

Das kann man, sollte man aber wahrscheinlich nicht:

try:
    do_something()
except:
    print("Caught it!")

Allerdings werden dabei auch Ausnahmen wie KeyboardInterrupt und das wollen Sie normalerweise nicht, oder? Es sei denn, Sie erhöhen die Ausnahme gleich wieder - siehe das folgende Beispiel aus den Unterlagen :

try:
    f = open('myfile.txt')
    s = f.readline()
    i = int(s.strip())
except IOError as (errno, strerror):
    print("I/O error({0}): {1}".format(errno, strerror))
except ValueError:
    print("Could not convert data to an integer.")
except:
    print("Unexpected error:", sys.exc_info()[0])
    raise

34 Stimmen

9 Stimmen

Sie sollten wirklich auf stderr drucken.

81 Stimmen

Ich widerspreche der Aussage "sollte nicht" sehr, sehr stark. Man sollte es sparsam einsetzen. Es kommt vor, dass man es mit Bibliotheken von Drittanbietern zu tun hat (die manchmal dynamisch geladen werden!!), die mit Ausnahmen völlig verrückt geworden sind, und sie alle aufzuspüren kann eine sehr schmerzhafte Aufgabe sein, und wenn man nur eine übersieht, hat man einen sehr, sehr großen, schmerzhaften Fehler in seinem System. Aus diesem Grund ist es gut, so viele wie möglich aufzuspüren und sie angemessen zu behandeln, und dann ein Backup für alle zu haben, die Sie übersehen.

186voto

gitaarik Punkte 36249

Um alle möglichen Ausnahmen abzufangen, fangen Sie BaseException . Sie steht in der Hierarchie der Ausnahmen ganz oben:

Python 3: https://docs.python.org/3.10/library/exceptions.html#exception-hierarchy

Python 2.7: https://docs.python.org/2.7/library/exceptions.html#exception-hierarchy

try:
    something()
except BaseException as error:
    print('An exception occurred: {}'.format(error))

Aber wie bereits von anderen erwähnt, ist dies in der Regel nicht erforderlich, sondern nur in sehr speziellen Fällen.

8 Stimmen

Ist es so ungewöhnlich, den Fortschritt eines lang laufenden Auftrags nach dem Drücken von Strg-C zu speichern?

0 Stimmen

Ich lasse meine Aufträge über einen HPC-Manager laufen. Ich möchte erfassen, wann der Manager (slurm, qsub, condor) einen Exit durchführt (um mich selbst mit meiner benutzerdefinierten E-Mail darüber zu informieren). Wird except: Haben Sie das verstanden? Aber es gibt mir keine Handhabe für e allerdings :(

2 Stimmen

In Python, all exceptions must be instances of a class that derives from BaseException aber wenn Sie es für einen allgemeinen Fall weglassen können - lassen Sie es weg, das Problem ist, Linters Wein darüber.

120voto

vwvolodya Punkte 2294

Sie können dies tun, um allgemeine Ausnahmen zu behandeln

try:
    a = 2/0
except Exception as e:
    print e.__doc__
    print e.message

12 Stimmen

Dadurch werden möglicherweise nicht alle Ausnahmen abgefangen, da die Basisklasse für alle Ausnahmen BaseException ist und ich in der Produktion auf Code gestoßen bin, der nicht zur Klassenfamilie Exception gehört. Siehe docs.python.org/3/library/ für Details dazu.

5 Stimmen

Dadurch werden nicht alle Ausnahmen abgefangen.

13 Stimmen

Technisch gesehen sollte sie alle nicht systembedingten Ausnahmen abfangen. Aus den von @DDay verlinkten Dokumenten: " Ausnahme BaseException: Die Basisklasse für alle eingebauten Ausnahmen. Sie ist nicht dafür gedacht, direkt an benutzerdefinierte Klassen vererbt zu werden (verwenden Sie dafür Exception)." Sofern Sie nicht mit Code arbeiten, der dies ignoriert, oder Sie müssen System-exiting Ausnahmen zu fangen, sollte die oben genannten ok zu verwenden.

65voto

Joshua Burns Punkte 7710

Ein sehr einfaches Beispiel, ähnlich dem, das Sie hier finden:

http://docs.python.org/tutorial/errors.html#defining-clean-up-actions

Wenn Sie versuchen, ALLE Ausnahmen abzufangen, dann fügen Sie Ihren gesamten Code in die "try:"-Anweisung ein, anstelle von 'print "Performing an action which may throw an exception."'.

try:
    print "Performing an action which may throw an exception."
except Exception, error:
    print "An exception was thrown!"
    print str(error)
else:
    print "Everything looks great!"
finally:
    print "Finally is called directly after executing the try statement whether an exception is thrown or not."

Im obigen Beispiel würden Sie die Ausgabe in dieser Reihenfolge sehen:

1) Ausführen einer Aktion, die eine Ausnahme auslösen kann.

2) Finally wird direkt nach der Ausführung der try-Anweisung aufgerufen, unabhängig davon, ob eine Ausnahme ausgelöst wird oder nicht.

3) "Eine Ausnahme wurde ausgelöst!" oder "Alles sieht gut aus!", je nachdem, ob eine Ausnahme ausgelöst wurde.

Ich hoffe, das hilft!

0 Stimmen

Ich lasse meine Aufträge über einen HPC-Manager laufen. Ich möchte erfassen, wenn der Manager (slurm, qsub, condor) einen Exit durchführt (um mich selbst mit meiner benutzerdefinierten E-Mail darüber zu informieren). Wird except: Haben Sie das verstanden? Aber es gibt mir keine Handhabe für e allerdings :(

2 Stimmen

Except Exception, error:^SyntaxError: ungültige Syntax

2 Stimmen

@Tony versuchen: except Exception as error: -- Wenn Sie Python3 verwenden.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X