[英]Best practice to add extra attributes for an object that related only to a specific class
[英]Best practice way for linking object attributes to class or object
我正在尋找一種可靠的pythonic方法,為某種類型的類屬性提供對它們所連接的類的反向引用。
即如果有類似下面的類定義,我想給SomeAttribute()
一個返回SomeClass
類型對象的引用。
class SomeClass(object):
attribute = SomeAttribute()
目前,我有一個實現,它在創建具有此類屬性的類后依賴於手動方法調用。 (以下示例)。 當前方法的問題在於,許多代碼需要檢查引用類是否已經在訪問時已填充到屬性。
一種解決方案是要求初始化類,在這種情況下, bind_attributes
的代碼可以放在__init__
方法中。 然而,即使不需要實例,這顯然也需要實例化類。 我相信使用元類可以實現更好的解決方案,但我不知道使用元類的pythonic實現如何。
import inspect
class Attribute(object):
def __init__(self, *params):
self._params = params
self._definition_class = None
def bind(self, definition_class):
self._definition_class = definition_class
def __call__(self):
return self._definition_class.separator.join(self._params)
class Definition(object):
separator = ', '
publications = Attribute('Books', 'Magazines')
clothes = Attribute('Shoes', 'Gloves', 'Hats')
@classmethod
def bind_attributes(cls):
for name, attribute in inspect.getmembers(cls, lambda m: isinstance(m, Attribute)):
attribute.bind(cls)
>>> Definition.bind_attributes()
>>> Definition.publications()
'Books, Magazines'
>>> Definition.clothes()
'Shoes, Gloves, Hats'
您可以使用元類來完成此操作。 例如:
class MyMeta(type):
def __new__(mcls, name, bases, members):
cls = type.__new__(mcls, name, bases, members)
for m in members.values():
if isinstance(m, SomeAttribute):
m.bound_cls = cls
return cls
現在當然有一個缺點是這個功能與類而不是屬性相關聯,因此您需要此功能的每個類都必須使用元類:
class SomeClass(object):
__metaclass__ = MyMeta
attribute = SomeAttribute()
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.