You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为什么Python Exception的repr会记录传入__init__的所有参数?

设计逻辑

Exception默认的__repr__保留所有构造入参,是专门为调试场景设计的:

  • 异常触发时,完整的入参是定位问题的核心上下文,哪怕自定义异常的__init__只用了参数的部分属性,默认保留全部原始入参可以避免调试时缺失关键信息,不需要开发人员额外手动记录入参
  • 异常作为错误信息载体,默认行为不做「参数是否有用」的假设,统一全量保留是适配所有业务场景的最低成本方案,如果有定制需求可以自行重写__repr__/__str__方法覆盖默认行为

运行原理伪代码

Exception的入参保存逻辑是在__new__方法里实现的,和子类是否重写__init__无关:

class BaseException:  # Python中所有异常的实际基类
    def __new__(cls, *args, **kwargs):
        # 实例化第一步就把所有位置参数存到内置args属性
        inst = super().__new__(cls)
        inst.args = args
        # 注:kwargs默认不会被存到args里,和原生行为一致
        return inst
    
    def __repr__(self):
        # 拼接repr时直接读取预存的args即可
        args_str = ", ".join(repr(a) for a in self.args)
        return f"{self.__module__}.{self.__class__.__name__}({args_str})"

# Exception继承自BaseException,继承了全部上述逻辑
class Exception(BaseException):
    pass

你给出的示例中,A(B())调用时,父类Exception的__new__会先执行,把B()实例存到args属性里,哪怕你重写的A.__init__只用到了b.message,也不会影响已经存好的args,所以__repr__会直接输出这个实例。而普通的自定义类没有这套预存入参+拼接入参的__repr__逻辑,所以只会输出默认的类名+内存地址格式。

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

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.08 21:12:00