Python:在__init__中引发异常是不好的形式?

mep*_*pum 111 python exception

是否认为在内部引发例外是不好的形式__init__?如果是这样,那么当某些类变量初始化为None或者类型不正确时,抛出错误的可接受方法是什么?

Joh*_*kin 145

提高内部异常__init__()绝对没问题.在构造函数中没有其他好的方法来指示错误条件,并且标准库中有数百个示例,其中构建对象可能引发异常.

当然,要提出的错误类由您决定.ValueError如果构造函数传递了无效参数,则最好.

  • 构造函数中最常用的异常是`ValueError`和`TypeError`. (14认同)
  • 只是指出`__init__`不是构造函数,它是初始化函数.您可能想要编辑行*没有其他好的方法来指示构造函数中的错误条件,..* (7认同)

Sep*_*rvi 23

确实,在构造函数中指示错误的唯一正确方法是引发异常.这就是为什么在C++和其他面向对象语言中考虑到异常安全性的原因,如果在对象的构造函数中抛出异常(意味着对象的初始化不完整),则不会调用析构函数.在脚本语言中通常不是这种情况,例如Python.例如,如果socket.connect()失败,则以下代码抛出AttributeError:

class NetworkInterface:
    def __init__(self, address)
        self.socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        self.socket.connect(address)
        self.stream = self.socket.makefile()

    def __del__(self)
        self.stream.close()
        self.socket.close()
Run Code Online (Sandbox Code Playgroud)

原因是在初始化流属性之前,在连接尝试失败后调用不完整对象的析构函数.你不应该避免从构造函数中抛出异常,我只是说在Python中编写完全异常安全的代码是很困难的.一些Python开发人员完全避免使用析构函数,但这是另一个争论的问题.


Eda*_*aor 11

我认为没有任何理由认为它应该是糟糕的形式.

相反,与返回错误代码相反,已知的异常事件之一就是错误代码通常不能由构造函数返回.所以至少在像C++这样的语言中,提出异常是发出错误信号的唯一方法.


sth*_*sth 5

标准库说:

>>> f = file("notexisting.txt")
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
IOError: [Errno 2] No such file or directory: 'notexisting.txt'
Run Code Online (Sandbox Code Playgroud)

我也没有看到任何理由为什么它应该被视为坏形式.