📜  Python|将异常引发到另一个异常

📅  最后修改于: 2022-05-13 01:55:41.914000             🧑  作者: Mango

Python|将异常引发到另一个异常

让我们考虑一种情况,我们希望引发异常以响应捕获不同的异常,但希望在回溯中包含有关这两个异常的信息。

要链接异常,请使用 raise from 语句而不是简单的 raise 语句。这将为您提供有关这两个错误的信息。

代码#1:

def example():
    try:
        int('N/A')
    except ValueError as e:
        raise RuntimeError('A parsing error occurred') from e...
  
example()

输出 :

Traceback (most recent call last):
  File "", line 3, in example
ValueError: invalid literal for int() with base 10: 'N/A'

此异常是以下异常的直接原因——

Traceback (most recent call last):
  File "", line 1, in 
  File "", line 5, in example
RuntimeError: A parsing error occurred

这两个异常都在回溯中捕获。普通的 except 语句用于捕获此类异常。但是,异常对象的__cause__属性可以被视为遵循异常链,如下面的代码中所述。

代码#2:

try:
    example()
except RuntimeError as e:
    print("It didn't work:", e)
    if e.__cause__:
        print('Cause:', e.__cause__)

当在 except 块内引发另一个异常时,会出现一种隐式形式的链式异常。

代码#3:

def example2():
    try:
        int('N/A')
    except ValueError as e:
        print("Couldn't parse:", err)
  
example2()
Traceback (most recent call last):
    File "", line 3, in example2
ValueError: invalid literal for int() with base 10: 'N / A'

在处理上述异常的过程中,又出现了一个异常:

Traceback (most recent call last):
    File "", line 1, in 
    File "", line 5, in example2
NameError: global name 'err' is not defined

在下面的代码中,NameError 异常是作为编程错误的结果引发的,而不是直接响应解析错误。对于这种情况,未设置异常的__cause__属性。相反,将__context__属性设置为先前的异常。

代码 #4:要禁止链接,请使用 raise from None

def example3():
    try:
        int('N / A')
    except ValueError:
        raise RuntimeError('A parsing error occurred') from None...
  
example3()

输出 :

Traceback (most recent call last):
    File "", line 1, in 
    File "", line 5, in example3
RuntimeError: A parsing error occurred