跳转到内容
彼岸论坛
欢迎抵达彼岸 彼岸花开 此处谁在 -彼岸论坛

[Python] Python 中 dataclass 风格定义异常类,正确吗?


小天管理

已推荐帖子

python 源码中有下面这样的异常定义:

class OSError(Exception):
    errno: int
    strerror: str
    # filename, filename2 are actually str | bytes | None
    filename: Any
    filename2: Any
    if sys.platform == "win32":
        winerror: int

因此我经常按上面的风格定义异常类,比如这次的:

class Error(Exception):
    code: str
    message: str

这样子写,一直工作良好。也许是因为我之前从没访问里面的属性? 这次,我写了下面的代码:

assert e.code in ("unauthorized", "permission")

收到很温馨的提示:

    assert e.code in ("unauthorized", "permission")
           ^^^^^^
AttributeError: 'Error' object has no attribute 'code'

问了 Claude ,回答为:

你提到的这种异常定义方法确实在 Python 源码中存在,特别是在类型提示和静态类型检查方面。这种定义方式主要用于类型注解和静态类型检查工具(如 mypy )。让我解释一下这种定义的目的和工作原理:

1. 类型注解的目的:
   这种定义主要是为了提供类型信息,而不是实际定义属性。它告诉类型检查器这个类预期会有哪些属性,以及这些属性的预期类型。

2. 运行时行为:
   这些注解在运行时不会创建实际的属性。实际的属性创建通常在类的 `__init__` 方法或其他方法中完成。

3. 兼容性和灵活性:
   这种方式允许在不改变运行时行为的情况下添加类型信息,这对于大型的、需要保持向后兼容性的项目(如 Python 标准库)非常有用。

4. 静态类型检查:
   静态类型检查工具可以使用这些注解来检查代码,即使这些属性可能在运行时动态创建。

5. 文档作用:
   这些注解也起到了文档的作用,告诉开发者这个类预期会有哪些属性。

在 `OSError` 的例子中,这些属性可能在异常被实际创建时(可能是在 C 代码中)被设置,而不是在 Python 的 `__init__` 方法中。

需要注意的是,这种定义方式主要用于 Python 的内置类型和标准库,在普通的 Python 代码中,我们通常会使用 `__init__` 方法来初始化属性,就像我在前面的回答中建议的那样。

对于你自己的代码,除非你有特殊需求(比如为了兼容性或与特定的类型检查工具配合),否则最好还是使用常规的方式定义和初始化属性。

你对这种定义方式还有其他疑问吗?或者你想了解更多关于 Python 类型注解的信息?
意见的链接
分享到其他网站

加入讨论

您现在可以发表并稍后注册. 如果您是会员,请现在登录来参与讨论.

游客
回复主题...

×   粘贴为富文本.   粘贴为纯文本来代替

  只允许使用75个表情符号.

×   您的链接已自动嵌入.   显示为链接来代替

×   您之前的内容已恢复.   清除编辑器

×   您无法直接粘贴图片.要从网址上传或插入图片.

  • 游客注册

    游客注册

  • 会员

    没有会员可显示

  • 最新的状态更新

    没有最新的状态更新
  • 最近查看

    • 没有会员查看此页面.
×
×
  • 创建新的...