super()是不是要与staticmethods一起使用?
当我尝试类似
时class First(object):
@staticmethod
def getlist():
return ['first']
class Second(First):
@staticmethod
def getlist():
l = super(Second).getlist()
l.append('second')
return l
a = Second.getlist()
print a
我收到以下错误
Traceback (most recent call last):
File "asdf.py", line 13, in <module>
a = Second.getlist()
File "asdf.py", line 9, in getlist
l = super(Second).getlist()
AttributeError: 'super' object has no attribute 'getlist'
如果我将staticmethods更改为classmethods并将类实例传递给super(),那么一切正常。我在这里打电话给超级(打字)还是我错过了什么?
答案 0 :(得分:46)
的简短回答
我在这里不正确地调用超级(类型)还是有些东西我不见了?
是:是的,你是错误地调用它...而且(实际上,因为)有一些你缺少的东西。
但不要心疼;这是一个非常困难的主题。
如果省略第二个参数,则返回的超级对象是未绑定的。
未绑定 super
对象的用例非常狭窄且极为罕见。请参阅Michele Simionato关于super()
的讨论的这些文章:
此外,他强烈主张从Python 3 here删除未绑定的super
。
我说你称它为“错误”(虽然没有上下文,正确性在很大程度上是无意义的,玩具示例并没有给出太多背景信息)。因为未绑定的super
是如此罕见,并且可能只是完全没有道理,正如Simionato所说,使用super()
的“正确”方法是提供第二个参数。
在您的情况下,让您的示例正常工作的最简单方法是
class First(object):
@staticmethod
def getlist():
return ['first']
class Second(First):
@staticmethod
def getlist():
l = super(Second, Second).getlist() # note the 2nd argument
l.append('second')
return l
a = Second.getlist()
print a
如果你认为这样看起来很有趣,那你就错了。但是我认为大多数人在看到super(X)
(或希望他们在自己的代码中尝试它们时)时所期待的是Python给你的super(X, X)
。
答案 1 :(得分:1)
当您在对象实例上调用普通方法时,该方法将接收对象实例作为第一个参数。它可以获取hte对象及其父类的类,因此调用super
是有意义的。
当您在对象实例或类上调用classmethod方法时,该方法将该类作为第一个参数接收。它可以获取父类,因此调用super
。
但是当你调用staticmethod方法时,该方法不会收到任何东西,也无法知道它被调用的对象或类。这就是您无法在静态方法中访问super
的原因。
答案 2 :(得分:0)
由于Second继承了First的形式,因此您只能使用First.getlist()
而不是在super(即super(Second, Second)
)中传入两个参数
class First(object):
@staticmethod
def getlist():
return ['first']
class Second(First):
@staticmethod
def getlist():
# l = super(Second, Second).getlist()
l = First.getlist()
l.append('second')
return l
a = Second.getlist()
print (a)