You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

如何导入内置traceback类以在Python类的__exit__方法中添加类型提示

为Python类的__exit__方法添加正确的类型提示

你说得对,__exit__方法的三个参数分别对应异常类型、异常实例和回溯对象,但直接写traceback: traceback会报错——因为你需要导入正确的回溯类型,而不是直接用模块名。

正确的导入与类型标注方式

回溯对象的实际类型是traceback.TracebackType,你需要从traceback模块导入这个类。另外,为了让类型提示更精准,我们还可以优化另外两个参数的类型:

  • typ 是异常类的类型,用 Type[BaseException] 比泛泛的 type 更准确,因为它只会是BaseException的子类类型
  • 三个参数都可能为None(当with块没有抛出异常时),所以要加上Optional标注这种情况

修改后的完整代码

from traceback import TracebackType
from typing import Type, Optional

class Foo:
    def __enter__(self):
        return self
    
    def __exit__(
        self,
        typ: Optional[Type[BaseException]],
        value: Optional[BaseException],
        traceback: Optional[TracebackType]
    ) -> bool:
        print(typ, value, traceback)
        print(type(typ), type(value), type(traceback))
        if traceback:
            print(type(traceback).__module__)
        return False  # 返回False表示不抑制异常,让异常继续向外传播

def main():
    with Foo():
        raise ValueError('Oops.')

if __name__ == '__main__':
    main()

补充说明

  1. 关于Optional:当with代码块正常执行没有抛出异常时,typvaluetraceback都会是None,用Optional标注能准确反映Python的实际行为。
  2. 返回值类型__exit__方法的返回值是布尔类型,返回True会告诉Python“这个异常已经被处理,不需要继续传播”,返回False(默认值)则会让异常继续向上抛出。
  3. 为什么用TracebackType:你运行代码时看到type(traceback).__module__traceback,这说明回溯对象的类型定义在traceback模块里,对应的类就是TracebackType,导入它之后就能正确完成类型标注了。

内容的提问来源于stack exchange,提问作者user3515670

火山引擎 最新活动