25

可以使用自定义文本引发内置异常吗?还是使用自定义文本也发出内置警告?

文档内容如下:

异常 ValueError:当内置操作或函数接收到参数时引发 (...)

是否暗示只有内置操作应该引发 ValueError 异常?

在实践中,我理解创建一个继承自 ValueError 或 Exception 的异常类是安全的。但是不这样做可以吗,直接引发ValueError(“自定义文本”)?

由于 ValueError 是内置的,与自定义异常类型(类似于“ValueErrorSpecificModule”,这不是标准的)相比,引发 ValueError(带有自定义文本)允许用户快速查看涉及哪种问题。

4

3 回答 3

28

执行以下操作在操作上没有任何问题:

raise ValueError("invalid input encoding")

事实上,当我编写一些代码的第一遍时,我经常这样做。这样做的主要问题是你的代码的客户很难准确处理他们的异常。为了捕获该特定异常,他们必须对捕获的异常对象进行字符串匹配,这显然是脆弱而乏味的。因此,最好引入自己的 ValueError 子类;这仍然可以作为 ValueError 捕获,但也可以作为更具体的异常类。

一般的经验法则是,只要您有如下代码:

raise ValueError('some problem: %s' % value)

您可能应该将其替换为以下内容:

class SomeProblem(ValueError):
    """
    Raised to signal a problem with the specified value.
    """
# ...
raise SomeProblem(value)

您可能会说异常类型指定出了什么问题,而消息/属性指定它是如何出错的。

于 2010-02-01T23:20:23.127 回答
3

没关系,我一直都这样做。在许多情况下,我发现 TypeError 比 MySpecialTypeError 更令人惊讶。

您链接的页面上,我没有看到“内置”一词:

exception TypeError: Raised when an operation or function is applied to an object of inappropriate type. The associated value is a string giving details about the type mismatch.

也许有人看到了您的问题并已经修复了文档。
编辑:看起来你可能已经插入了文档ValueError而不是TypeError

于 2010-02-01T22:48:45.290 回答
3

完全没问题。

但是,您可能希望创建自己的子类以帮助区分内置异常

例如,如果您有类似 a 的东西dict,您可以出于通常的原因引发 KeyError,但如果 KeyError 真的来自您在实现中使用的底层 dict 怎么办。

提高 KeyError 的子类可以更容易地看到实现中存在错误,而不是密钥不在您的对象中

于 2010-02-01T22:44:28.413 回答