Python super() 参数:为什么不是 super(obj)? [英] Python super() arguments: why not super(obj)?

查看:32
本文介绍了Python super() 参数:为什么不是 super(obj)?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图了解何时以及如何在 Python 中正确使用 super()(2.7.x 或 3.x)

I am trying to understand when and how to use super() in Python correctly (either 2.7.x or 3.x)

关于<代码>>>>help(super) 解释器告诉我如何调用它:

on >>> help(super) the interpreter tells me how to call it:

class super(object)
 |  super(type) -> unbound super object
 |  super(type, obj) -> bound super object; requires isinstance(obj, type)
 |  super(type, type2) -> bound super object; requires issubclass(type2, type)

我知道在 Python3.x 中现在可以在类定义中使用 super(),但我不明白为什么 super(obj) 是不可能的.或 super(self) 在类定义中.

I understand that in Python3.x it's now possible to juse use super() within a class definition, but I don't understand why super(obj) is not possible. Or super(self) within a class definition.

我知道一定有原因,但我找不到.对我来说,这些行相当于 super(obj.__class__, obj)super(self.__class__, self) 那些行吗?

I know there must be a reason for it, but I can't find it. To me those lines are equivalent to super(obj.__class__, obj) or super(self.__class__, self) and those would work right?

我认为即使在 Python 3.x 中,只要输入 super(obj) 也是一个不错的快捷方式.

I would think that just typing super(obj) would be a nice shortcut even in Python 3.x.

推荐答案

双参数形式只在 Python 2 中需要.原因是 self.__class__ 总是指叶子"继承树中的类——也就是对象最具体的类——但是当你调用 super 时你需要告诉它当前正在调用哪个实现,以便它可以调用下一个在继承树中.

The two-argument form is only needed in Python 2. The reason is that self.__class__ always refers to the "leaf" class in the inheritance tree -- that is, the most specific class of the object -- but when you call super you need to tell it which implementation is currently being invoked, so it can invoke the next one in the inheritance tree.

假设你有:

class A(object):
   def foo(self):
      pass

class B(A):
   def foo(self):
      super(self.__class__, self).foo()

class C(B):
   def foo(self):
      super(self.__class__, self).foo()

c = C()

请注意,c.__class__ 始终是 C.现在想想如果你调用 c.foo() 会发生什么.

Note that c.__class__ is C, always. Now think about what happens if you call c.foo().

当你在 C 的方法中调用 super(self.__class__, self) 时,就像调用 super(C, self),意思是调用由 C 继承的此方法的版本".这将调用 B.foo,这很好.但是当你从B调用super(self.__class__, self)时,还是像调用了super(C, self),因为是同一个self,所以 self.__class__ 仍然是 C.结果是 B 中的调用将再次调用 B.foo 并发生无限递归.

When you call super(self.__class__, self) in a method of C, it will be like calling super(C, self), which means "call the version of this method inherited by C". That will call B.foo, which is fine. But when you call super(self.__class__, self) from B, it's still like calling super(C, self), because it's the same self, so self.__class__ is still C. The result is that the call in B will again call B.foo and an infinite recursion occurs.

当然,您真正想要的是能够调用super(classThatDefinedTheImplementationThatIsCurrentlyExecuting, self),而这实际上是Python 3 super() 所做的.

Of course, what you really want is to be able to call super(classThatDefinedTheImplementationThatIsCurrentlyExecuting, self), and that is effectively what the Python 3 super() does.

在 Python 3 中,你可以只做 super().foo() 并且它做正确的事情.我不清楚你所说的 super(self) 作为快捷方式是什么意思.在 Python 2 中,由于我上面描述的原因,它不起作用.在 Python 3 中,这将是一个长切",因为您可以使用普通的 super() 代替.

In Python 3, you can just do super().foo() and it does the right thing. It's not clear to me what you mean about super(self) being a shortcut. In Python 2, it doesn't work for the reason I described above. In Python 3, it would be a "longcut" because you can just use plain super() instead.

super(type)super(type1, type2) 在 Python 3 中可能偶尔仍然需要使用,但对于异常情况,这些用法总是更深奥的用法.

The super(type) and super(type1, type2) uses might still be needed occasionally in Python 3, but those were always more esoteric usages for unusual situations.

这篇关于Python super() 参数:为什么不是 super(obj)?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆