2010-11-10 86 views
2

我有一组类可以包含可选的name属性。原因是如果设置了属性,类将获得默认名称,但如果需要,单个类仍可以具有自定义名称。Python属性也作为类属性

我想要的是能够从类(没有任何类实例)和类的实例中获取名称属性。

class NameMixin(object): 
    def _get_name(self): 
     if getattr(self, '_name', ''): 
      return self._name 
     else: 
      return self.__class__.__name__ 

    def _set_name(self, name): 
     self._name = name 

    name = property(_get_name, _set_name) 

class A(NameMixin): 
    name = 'Class A' 

class B(NameMixin): 
    pass 

这里,类A定制的名称,而类B没有。

>>> a = A() 
>>> a.name 
'Class A' 
>>> A.name 
'Class A' 

正如所看到的,这个工作,因为它应该

>>> b = B() 
>>> b.name 
'B' 
>>> B.name 
<property object at 0x7fd50a38c578> 

这不工作,我想要的!从特定实例获取名称的工作方式应该如此,但尝试从该类中获取名称将返回property object

是否有可能直接从类获取名称,而不通过与属性对象箍跳(这我真的不能在地方检查,我需要的类属性反正。)

回答

1
class NameMixinMeta(type): 
    def _get_name(self): 
     return getattr(self, '_name', self.__name__) 

    def _set_name(self, name): 
     self._name = name 

    name = property(_get_name, _set_name) 

class NameMixin(object): 
    __metaclass__ = NameMixinMeta 
    def _get_name(self): 
     return getattr(self, '_name', self.__class__.__name__) 

    def _set_name(self, name): 
     self._name = name 

    name = property(_get_name, _set_name) 

class A(NameMixin): 
    _name = 'Class A' 

class B(NameMixin): 
    pass 
+0

嗯...差不多工作... A.name返回'A'这是不完全正确的。然而,你使用元类让我思考,而且似乎我有一个可行的解决方案。我将跳过属性和mixins,并且在metaclass中,我将覆盖'__new__'并在字典中添加'name'(如果它不存在)。 – 2010-11-10 10:14:32

0

我我不确定你的NameMixin班是否在这里工作。

在第一种情况下,name是一个类属性,可以像你说的那样访问它。

>>> class A(): 
...  name = 'Class A' 
... 
>>> 
>>> a = A() 
>>> a.name 
'Class A' 
>>> A.name 
'Class A' 
>>> 

在第二种情况下,NameMixin类具有按照您的建议返回属性的效果。