Wie deaktiviere ich Zusicherungen in Python?
Das heißt, wenn eine Behauptung fehlschlägt, möchte ich nicht, dass sie eine wirft AssertionError
, sondern weiter macht.
Wie mache ich das?
Wie deaktiviere ich Zusicherungen in Python?
Das heißt, wenn eine Behauptung fehlschlägt, möchte ich nicht, dass sie eine wirft AssertionError
, sondern weiter macht.
Wie mache ich das?
Wie deaktiviere ich Zusicherungen in Python?
Es gibt mehrere Ansätze, die sich auf einen einzelnen Prozess, die Umgebung oder eine einzelne Codezeile auswirken.
Ich demonstriere jeden.
Die Verwendung des -O
Flags (Großbuchstabe O) deaktiviert alle Assert-Anweisungen in einem Prozess.
Beispielsweise:
$ python -Oc "assert False"
$ python -c "assert False"
Traceback (most recent call last):
File "<string>", line 1, in <module>
AssertionError
Beachten Sie, dass mit deaktivieren gemeint ist, dass der darauf folgende Ausdruck auch nicht ausgeführt wird:
$ python -Oc "assert 1/0"
$ python -c "assert 1/0"
Traceback (most recent call last):
File "<string>", line 1, in <module>
ZeroDivisionError: integer division or modulo by zero
Sie können dieses Flag auch mit einer Umgebungsvariablen setzen.
Dies wirkt sich auf jeden Prozess aus, der die Umgebung verwendet oder erbt.
Beispiel: Setzen und löschen Sie in Windows die Umgebungsvariable:
C:\>python -c "assert False"
Traceback (most recent call last):
File "<string>", line 1, in <module>
AssertionError
C:\>SET PYTHONOPTIMIZE=TRUE
C:\>python -c "assert False"
C:\>SET PYTHONOPTIMIZE=
C:\>python -c "assert False"
Traceback (most recent call last):
File "<string>", line 1, in <module>
AssertionError
Gleiches unter Unix (mit set und unset für die jeweilige Funktionalität)
Sie setzen Ihre Frage fort:
Wenn eine Assertion fehlschlägt, möchte ich nicht, dass sie einen AssertionError auslöst, sondern dass sie weitergeht.
Wenn Sie möchten, dass der Code nicht ausgeführt wird, können Sie entweder sicherstellen, dass der Kontrollfluss die Behauptung nicht erreicht, zum Beispiel:
if False:
assert False, "we know this fails, but we don't get here"
oder Sie können den Assertionsfehler abfangen:
try:
assert False, "this code runs, fails, and the exception is caught"
except AssertionError as e:
print(repr(e))
welche druckt:
AssertionError('this code runs, fails, and the exception is caught')
und Sie werden von dem Punkt an weitermachen, an dem Sie das erledigt haben AssertionError
.
Aus der assert
Dokumentation :
Eine Aussage wie diese:
assert expression #, optional_message
Ist äquivalent zu
if __debug__: if not expression: raise AssertionError #(optional_message)
Und,
Die integrierte Variable
__debug__
befindet sichTrue
unter normalen Umständen,False
wenn eine Optimierung angefordert wird (Befehlszeilenoption-O
).
und weiter
Aufträge an
__debug__
sind illegal. Der Wert für die integrierte Variable wird beim Start des Interpreters festgelegt.
Aus den Verwendungsdokumenten:
Aktivieren Sie grundlegende Optimierungen. Dadurch wird die Dateinamenerweiterung für kompilierte (Bytecode-) Dateien von .pyc in .pyo geändert. Siehe auch PYTHONOPTIMIEREN.
und
Wenn dies auf eine nicht leere Zeichenfolge festgelegt ist, entspricht dies der Angabe der
-O
Option. Wenn eine Ganzzahl festgelegt ist, entspricht dies einer-O
mehrfachen Angabe .
__debug__
auf False zu setzen, aber das ist nicht erlaubt.if False: assert False
), oder Sie können den Assertion-Fehler abfangen. Das sind deine Entscheidungen. Die Antwort wurde aktualisiert, um Ihre Frage zu beantworten.foo()
und Assertions ausschalten :with skip_assertion(): foo()
. Der Vorteil davon ist, dass ich kein weiteres Flag auf der Funktion hinzufügen mussAssert
Objekte durchPass
Objekte ersetzen ). Ein Kontextmanager würde dafür nicht direkt arbeiten, aber Sie könnten einen Mechanismus haben, der dekorierte Funktionen auf diese Weise verwendet. Trotzdem empfehle ich es nicht. Ich vermute, Ihr Grund dafür ist, dass Sie Code aufrufen, den Sie nicht kontrollieren, und AssertionErrors erhalten. In diesem Fall müssen Sie wahrscheinlich einen anderen Fix finden.Rufen Sie Python mit dem Flag -O auf:
test.py:
Ausgabe:
quelle
Beide bereits gegebenen Antworten sind gültig (rufen Sie Python entweder mit
-O
oder-OO
über die Befehlszeile auf).Hier ist der Unterschied zwischen ihnen:
-O
Aktivieren Sie grundlegende Optimierungen. Dadurch wird die Dateinamenerweiterung für kompilierte (Bytecode-) Dateien von .pyc in .pyo geändert.-OO
Verwerfen Sie zusätzlich zu den-O
Optimierungen Dokumentzeichenfolgen .(Aus der Python-Dokumentation )
quelle
Verwendung
python -O
:quelle
Sie sollten (die meisten) Zusicherungen NICHT deaktivieren. Sie fangen unerwartete Fehler auf, wenn die Aufmerksamkeit woanders liegt. Siehe Regel 5 in "Die Zehnerpotenz" .
Bewachen Sie stattdessen einige teure Assertionsprüfungen wie folgt:
Eine Möglichkeit, wichtige Aussagen beizubehalten und die
assert
Optimierung von Anweisungen zu ermöglichen, besteht darin, sie in einer Auswahlanweisung anzuheben:quelle
Das Ausführen im optimierten Modus sollte dies tun:
quelle