我在 Python 3.7 中遇到了一些在子類化時我不明白的行為 Exception
我使用 Python 已經很長時間了,我一直認為基類建構式不是隱式的,必須顯式呼叫。
例如,下面的行為與我的理解是一致的,因為A永遠不會呼叫的建構式x不會被定義。
class A():
def __init__(self, x):
self.x = x
class B(A):
def __init__(self, x):
pass
b = B(1)
print(b.x)
AttributeError: 'B' object has no attribute 'x'
但是在下面的示例中,當我沒有明確地Exception將訊息hello提供給基類??建構式時,我不明白基類是如何接收訊息的。
class E(Exception):
def __init__(self, msg):
# don't do anything with msg
pass
raise E("hello")
__main__.E: hello
uj5u.com熱心網友回復:
我相信 Exception 類有一個特殊的__new__()函式來跟蹤傳入的引數。在 Python 3.6.10 中,我嘗試忽略傳入的第一個引數__new__(),但它不顯示傳入的引數。
class E2(Exception):
def __new__(cls, msg, *args, **kwargs):
# ignore the msg argument passed in
return super().__new__(cls, *args, **kwargs)
def __init__(self, msg):
# also ignore the msg passed in
pass
raise E2("hello")
這會列印一條沒有“hello”的錯誤訊息
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
__main__.E2
uj5u.com熱心網友回復:
通過查看源代碼,BaseException類有一個BaseException_new實作(相當于__new__python層),它在創建程序中將所有引數系結到例外實體。
靜態 PyObject *
BaseException_new(PyTypeObject *type, PyObject *args , PyObject *kwds)
{
PyBaseExceptionObject *self;
self = (PyBaseExceptionObject *)type->tp_alloc(type, 0);
如果(!自我)
回傳空;
/* dict 是在 PyObject_GenericSetAttr 中動態創建的 */
self->dict = NULL;
self->traceback = self->cause = self->context = NULL;
self->suppress_context = 0;
如果(引數){
自我-> args = args;
Py_INCREF(args);
回傳(PyObject *)自我;
}
self->args = PyTuple_New(0);
如果 (!self->args) {
Py_DECREF(自我);
回傳空;
}
回傳(PyObject *)自我;
}
您可以確認這是在 python 層中。
>>> class E(Exception):
... def __init__(self, msg):
... pass
...
>>>
>>> a = E("hello")
>>> a.args
('hello',)
轉載請註明出處,本文鏈接:https://www.uj5u.com/gongcheng/369948.html
