我试图了解 Python 如何在异常处理中处理异常。例如,请考虑以下内容:
try:
try:
1/0
finally:
raise Exception("Exception!")
except Exception as e:
print(e)
我的理解是,这段代码抛出的两个异常(ZeroDivisionError 和 finally 块中抛出的通用异常)都应该由除了块之外的外部“处理”……但是 Python 如何决定分配给哪个异常e?在我的机器上运行代码,似乎Python选择将“最近的”异常(finally块中抛出的那个)分配给e。
这通常是真的吗?此外,在这种情况下,在错误处理中可能会抛出多个异常,而这些异常都由外部 except 块处理,有没有办法让外部 except 块分别单步处理每个错误?
答案 0 :(得分:2)
Python docs 有这个:
<块引用>如果在 try 子句执行过程中发生异常,则 异常可以由except子句处理。如果异常不是 由except子句处理,异常在 finally 子句已执行。
因此,在您的示例中,您没有捕获内部异常,这会导致 finally
块执行(在重新引发原始异常之前)。 finally
中的异常在有机会重新引发原始异常之前将其踢到外部块。外部块永远不会看到被零除异常。
这类似于 return
中的函数的 finally
ing:
def ex_test():
try:
try:
1/0
finally:
return "finally"
except Exception as e:
print(e) # never gets here
ex_test()
# only prints "finally"
# never re-raises the exception
您可以获得一些关于原始异常的信息。来自the docs:
<块引用>在except或finally中引发(或重新引发)异常时 context 子句自动设置为最后捕获的异常; 如果新的异常没有被处理,那么最终的回溯 显示的将包括原始异常和最终异常 例外。
所以:
try:
try:
1/0
finally:
raise Exception("Exception!")
except Exception as e:
print(e.__context__)
# prints: "division by zero"