【发布时间】:2019-06-18 21:33:19
【问题描述】:
当使用 __new__ 自定义创建元类时,我们可以将属性传递给 type().__new__ 方法,该方法将在对象返回之前对其进行设置,例如
class Foo(type):
def __new__(cls, name, bases, attrs):
attrs['customAttr'] = 'someVal'
return type.__new__(cls, name, bases, attrs)
这样:
>> Foo.__dict__
{'customeAttr': 'someVal', ...}
但是我不知道如何对普通(非元)类执行相同操作,这会在使用 __setattr__ 时导致问题:
class Bar(object):
def __new__(cls, someVal):
obj = object().__new__(cls) # cant pass custom attrs
obj.customAttr = someVal # obj is already a Bar and invokes __setattr__
return obj
def __setattr__(*args): raise Exception('read-only class')
不幸的是:
>>> Bar(42)
...
Exception: read-only class
在 Bar 的 __new__ 中,我从 object() 中获取了一个完全成熟的类实例,并且任何属性访问都通过正常的查找规则,在本例中调用 __setattr__。元类 Foo 避免了这种情况,因为 type() 会在低级创建期间返回实例之前设置属性,而 object() 不会。
有没有一种方法可以将属性传递给 object() 或者我可以使用另一种类型作为从 __new__ 返回的实例,它允许在属性成为完整的类实例之前设置属性?我对在创建实例后设置 __class__ 之类的解决方案不感兴趣。
【问题讨论】:
标签: python object metaprogramming dynamic-class-creation