我想知道如何在没有输出回溯转储的情况下退出 Python。
我仍然希望能够返回错误代码,但我不想显示回溯日志。
我希望能够在没有跟踪的情况下使用 exit(number)
退出,但如果出现异常(不是退出),我想要跟踪。
您可能遇到了异常,因此程序正在退出(带有回溯)。因此,首先要做的是在干净退出之前捕获该异常(可能带有消息,给出示例)。
在您的 main
例程中尝试这样的操作:
import sys, traceback
def main():
try:
do main program stuff here
....
except KeyboardInterrupt:
print "Shutdown requested...exiting"
except Exception:
traceback.print_exc(file=sys.stdout)
sys.exit(0)
if __name__ == "__main__":
main()
也许您正试图捕捉所有异常,而这正是捕捉由 sys.exit()
引发的 SystemExit
异常?
import sys
try:
sys.exit(1) # Or something that calls sys.exit()
except SystemExit as e:
sys.exit(e)
except:
# Cleanup and reraise. This will print a backtrace.
# (Insert your cleanup code here.)
raise
通常,使用 except:
而不命名异常是一个坏主意。你会捕捉到各种你不想捕捉的东西——比如SystemExit
——它还可以掩盖你自己的编程错误。我上面的例子很愚蠢,除非你在清理方面做一些事情。您可以将其替换为:
import sys
sys.exit(1) # Or something that calls sys.exit().
如果您需要在不提高 SystemExit
的情况下退出:
import os
os._exit(1)
我在 unittest 下运行并调用 fork()
的代码中执行此操作。当分叉的进程引发 SystemExit
时,单元测试得到。这绝对是一个极端案例!
SystemExit
只是为了调用 sys.exit(e)
?删除这两行具有 same 效果。此外,清理属于 finally:
,而不是 except Exception: ... raise
。
import sys
sys.exit(1)
以下代码不会引发异常,并且会在没有回溯的情况下退出:
import os
os._exit(1)
See this question and related answers 了解更多详情。很惊讶为什么所有其他答案都如此复杂。
这也不会进行适当的清理,例如调用清理处理程序、刷新 stdio 缓冲区等(感谢 pabouk 指出这一点)
import sys; sys.exit(0)
之类的东西?
避免使用 sys.exit() 而是引发/处理异常以允许程序干净地完成是更好的做法。如果要关闭回溯,只需使用:
sys.trackbacklimit=0
您可以在脚本顶部设置它以压缩所有回溯输出,但我更喜欢谨慎使用它,例如我希望输出干净的“已知错误”,例如在文件 foo.py 中:
import sys
from subprocess import *
try:
check_call([ 'uptime', '--help' ])
except CalledProcessError:
sys.tracebacklimit=0
print "Process failed"
raise
print "This message should never follow an error."
如果 CalledProcessError 被捕获,输出将如下所示:
[me@test01 dev]$ ./foo.py
usage: uptime [-V]
-V display version
Process failed
subprocess.CalledProcessError: Command '['uptime', '--help']' returned non-zero exit status 1
如果发生任何其他错误,我们仍然会获得完整的回溯输出。
sys.trackbacklimit
,请参阅 this answer。
stderr
,而不是 stdout
。改用这个:print("Process failed", file=sys.stderr)
使用内置的 python 函数 quit() 就是这样。无需导入任何库。我正在使用 python 3.4
quit()
或 exit()
。这些函数仅适用于交互式 Python。请参阅 Python exit commands - why so many and when should each be used? 您可以改用 sys.exit()
或 raise SystemExit
。
我会这样做:
import sys
def do_my_stuff():
pass
if __name__ == "__main__":
try:
do_my_stuff()
except SystemExit, e:
print(e)
关于什么
import sys
....
....
....
sys.exit("I am getting the heck out of here!")
没有回溯,并且以某种方式更明确。
# Pygame Example
import pygame, sys
from pygame.locals import *
pygame.init()
DISPLAYSURF = pygame.display.set_mode((400, 300))
pygame.display.set_caption('IBM Emulator')
BLACK = (0, 0, 0)
GREEN = (0, 255, 0)
fontObj = pygame.font.Font('freesansbold.ttf', 32)
textSurfaceObj = fontObj.render('IBM PC Emulator', True, GREEN,BLACK)
textRectObj = textSurfaceObj.get_rect()
textRectObj = (10, 10)
try:
while True: # main loop
DISPLAYSURF.fill(BLACK)
DISPLAYSURF.blit(textSurfaceObj, textRectObj)
for event in pygame.event.get():
if event.type == QUIT:
pygame.quit()
sys.exit()
pygame.display.update()
except SystemExit:
pass
except Exception:
到sys.exit(0)
的行,包括在内。在所有未处理的异常上打印回溯并在代码结束后退出已经是默认行为,那么为什么还要手动执行相同的操作呢?sys.exit()
应该用于程序。exit()
用于交互式 shell。请参阅The difference between exit() and sys.exit() in Python?。