Ответ 1
Нет никакой практической разницы, но есть и другая разница в вашем примере кода - print
переходит в стандартную версию, но текст исключения идет на стандартную ошибку (что, вероятно, вы хотите).
Чтение онлайн-программистов использует sys.exit
, другие используют SystemExit
.
Извините за основной вопрос:
Пример
ref = osgeo.ogr.Open(reference)
if ref is None:
raise SystemExit('Unable to open %s' % reference)
или
ref = osgeo.ogr.Open(reference)
if ref is None:
print('Unable to open %s' % reference)
sys.exit(-1)
Нет никакой практической разницы, но есть и другая разница в вашем примере кода - print
переходит в стандартную версию, но текст исключения идет на стандартную ошибку (что, вероятно, вы хотите).
sys.exit(s)
является просто сокращением для raise SystemExit(s)
, как описано в предыдущей документации; попробуйте help(sys.exit)
. Итак, вместо одной из ваших примерных программ вы можете сделать
sys.exit('Unable to open %s' % reference)
Есть 3 функции выхода, помимо повышения SystemExit
.
Ниже приведена os._exit
, которая требует 1 int аргумента и немедленно выйдет без очистки. Вряд ли вы когда-нибудь захотите коснуться этого, но он есть.
sys.exit
определяется в sysmodule.c и просто запускается PyErr_SetObject(PyExc_SystemExit, exit_code);
, что фактически совпадает с прямым повышением SystemExit
. В мельчайших деталях повышение SystemExit
возможно быстрее, поскольку sys.exit
требует опций LOAD_ATTR
и CALL_FUNCTION
vs RAISE_VARARGS
. Кроме того, raise SystemExit
создает немного меньший байт-код (на 4 байта), (1 байт дополнительно, если вы используете from sys import exit
, поскольку ожидается, что sys.exit
возвращает None, поэтому включает дополнительный POP_TOP
).
Последняя функция выхода определена в site.py
и с псевдонимом exit
или quit
в REPL. Это фактически экземпляр класса Quitter
(поэтому он может иметь пользовательский __repr__
, поэтому, вероятно, это самый медленный запуск. Кроме того, он закрывает sys.stdin
до повышения SystemExit
, поэтому он рекомендуется использовать только в REPL.
Что касается обработки SystemExit
, это в конечном итоге приводит к тому, что виртуальная машина вызывает os._exit, но до этого она выполняет некоторую очистку. Он также запускает atexit._run_exitfuncs()
, который выполняет любые обратные вызовы, зарегистрированные через модуль atexit
. Вызов os._exit
напрямую обходит шаг atexit
.
Мои личные предпочтения заключаются в том, что по крайней мере SystemExit
поднимается (или даже лучше - более значимое и хорошо документированное пользовательское исключение), а затем оказывается как можно ближе к основной функции, которая может иметь последний шанс считать его действительным выходом или нет. Библиотеки/глубоко внедренные функции, имеющие sys.exit
, просто противны с дизайнерской точки зрения. (Как правило, выход должен быть "как можно выше" )
SystemExit
- это исключение, которое в основном означает, что ваша прогама имела такое поведение, что вы хотите остановить ее и вызвать ошибку. sys.exit
- это функция, которую вы можете вызывать для выхода из вашей программы, что дает код возврата в систему.
EDIT: они действительно одно и то же, поэтому единственная разница в логике, стоящей в вашей программе. Исключением является какое-то "нежелательное" поведение, независимо от того, является ли вызов функции с точки зрения программиста более "стандартным" действием.
В соответствии с документацией sys.exit(s)
эффективно делает raise SystemExit(s)
, так что это почти то же самое.
Как вы можете прочитать здесь: Разница между exit() и sys.exit() в Python sys.exit(...) выполняет некоторую очистку и очищает буферы stdio, а после очистки очищает SysExit
если вы хотите напечатать сообщение об ошибке, вы можете просто сказать: "sys.exit(" сообщение об ошибке ") вместо того, чтобы делать печать раньше и" сообщение об ошибке "будет напрямую перейти к stderr вместо stdout, такое же поведение, как" raise SysError ( "сообщение об ошибке" )".
Таким образом, если вы хотите выйти, вы должны предпочесть sys.exit только для повышения SysExit, sys.exit(...) можно поймать так же, как только повышение SysExit и sys.exit(0) больше читаемый, чем "поднять SysExit", на мой взгляд.