Ara*_*Fey 7 python super python-3.x
在调查这个问题时,我遇到了单一参数的奇怪行为super:
调用super(some_class).__init__()在some_class(或其子类)的方法内部工作,但在其他地方调用时抛出异常.
代码示例:
class A():
def __init__(self):
super(A).__init__() # doesn't throw exception
a = A()
super(A).__init__() # throws exception
Run Code Online (Sandbox Code Playgroud)
抛出的异常是
Traceback (most recent call last):
File "untitled.py", line 8, in <module>
super(A).__init__() # throws exception
RuntimeError: super(): no arguments
Run Code Online (Sandbox Code Playgroud)
我不明白为什么电话的位置有所不同.
众所周知,super 执行魔法的零参数形式:
零参数形式仅适用于类定义,因为编译器填写必要的细节以正确检索正在定义的类,以及访问普通方法的当前实例.
但是,对于单参数形式,没有这样的陈述super.反之:
另请注意,除零参数形式外,super()不限于使用内部方法.
所以,我的问题是,引擎盖下究竟发生了什么?这是预期的行为吗?
在这两种情况下,super(A)都会给出一个未绑定的超级对象。当你调用__init__()它时,它会被无参数地调用。当super.__init__不带参数调用时,编译器尝试推断参数:(来自 typeobject.c 第 7434 行,最新源代码)
static int
super_init(PyObject *self, PyObject *args, PyObject *kwds)
{
superobject *su = (superobject *)self;
PyTypeObject *type = NULL;
PyObject *obj = NULL;
PyTypeObject *obj_type = NULL;
if (!_PyArg_NoKeywords("super", kwds))
return -1;
if (!PyArg_ParseTuple(args, "|O!O:super", &PyType_Type, &type, &obj))
return -1;
if (type == NULL) {
/* Call super(), without args -- fill in from __class__
and first local variable on the stack. */
Run Code Online (Sandbox Code Playgroud)
几行之后:(同上,第 7465 行)
f = PyThreadState_GET()->frame;
...
co = f->f_code;
...
if (co->co_argcount == 0) {
PyErr_SetString(PyExc_RuntimeError,
"super(): no arguments");
return -1;
}
Run Code Online (Sandbox Code Playgroud)
当您调用 时super(A),会绕过此推断行为,因为类型不是 None。然后,当您调用__init__()未绑定的 super 时 - 因为它未绑定,所以该__init__调用不会被代理 - 类型参数为None 并且编译器尝试推断。在类定义内部,存在 self 参数并用于此目的。在外部,没有可用的参数,因此引发异常。
换句话说,super(A)并不是根据调用位置的不同而表现不同 - 而是表现super.__init__()不同,而这正是文档所建议的。
| 归档时间: |
|
| 查看次数: |
216 次 |
| 最近记录: |