因此基类中有一个静态方法,子类应该使用它。
但是,我需要知道哪个子类调用静态方法。
代码是这样的:
class BaseClass():
@staticmethod
def getname():
#some magic
class SubClassA(BaseClass):
pass
class SubClassB(BaseClass):
pass
SubClassA.getname() #hope to see 'SubClassA'
SubClassB.getname() #hope to see 'SubClassB'
或者,这甚至可能吗?
答案 0 :(得分:3)
无法使用staticmethod
。但是,classmethod
class A(object):
@classmethod
def f(cls):
print cls
答案 1 :(得分:2)
根据定义,staticmethod
没有提供对调用类或实例的引用 - 这就是Python中“静态”的含义。
你可以做一些hacky事情来实现这一点,使用元类或装饰器。
请注意,我使用的是从帖子中获取类名称的示例,但是,您可以修改此示例以使用您希望作为静态函数的任何类型的函数。你只需在下面getnameable
中定义该函数,就像我已定义getname
并使用下面的some_class
参数一样(并且你使用的名称不同于所有“getname”)我在这里使用的东西)。
使用装饰器,你可以这样做:
def getnameable(some_class):
# Note, this could be any kind of static method that you want, not
# just for getting the name. And it can use `some_class` in whatever
# way is needed.
def getname():
return some_class.__name__
some_class.getname = staticmethod(getname)
return some_class
然后这可行:
In [334]: @getnameable
class SubClassA(BaseClass):
pass
.....:
In [335]: SubClassA.getname()
Out[335]: 'SubClassA'
但请注意,如果您直接在BaseClass
中实现了此功能,则绑定的类名称将为BaseClass
,即使在子类中也是如此。所以在这种情况下,你需要将装饰器放在你想要的每个类上。
元类通过表明你希望这个装饰类的业务成为类创建的一部分(而不是实例创建,请注意),提供了大量的东西。
class GetNameableMeta(type):
def __new__(cls, name, bases, attrs):
temp_class = super(GetNameableMeta, cls).__new__(cls, name, bases, attrs)
return getnameable(temp_class)
class BaseClass(object):
__metaclass__ = GetNameableMeta
class SubClassA(BaseClass):
pass
测试出来:
In [337]: %cpaste
Pasting code; enter '--' alone on the line to stop or use Ctrl-D.
:class GetNameableMeta(type):
: def __new__(cls, name, bases, attrs):
: temp_class = super(GetNameableMeta, cls).__new__(cls, name, bases, attrs)
: return getnameable(temp_class)
:
:class BaseClass(object):
: __metaclass__ = GetNameableMeta
:
:class SubClassA(BaseClass):
: pass
:--
In [338]: SubClassA.getname()
Out[338]: 'SubClassA'
In [339]: BaseClass.getname()
Out[339]: 'BaseClass'
当我们有几个合理的选择时,请注意我们需要编写多少高falutin代码来执行此操作:
__name__
属性。classmethod
。我怀疑在“Python的本质”中,任何这些都比我上面描述的机制更好,因为它使代码更简单,更容易理解。