2012-02-29 69 views
-1

我想用循环创建一系列对象属性。具体来说,我想通过将功能列表应用于现有属性来生成“次要”属性。 我的尝试显示在名为gen_secondary_properties的函数中,如下所示。问题是所有的属性都是相等的,我不知道为什么。装饰器的动态属性

def gen_secondary_properties(sefl): 
    prop_dict = { 
     's' : self.s, 
     'y' : self.y, 
     'z' : self.z, 
     } 
    func_dict = { 
     'real': npy.real, 
     'imag': npy.imag, 
     } 
    for prop_key in prop_dict: 
     for func_key in func_dict: 
      fget = lambda self: func_dict[func_key](prop_dict[prop_key]) 
      setattr(self.__class__,'%s_%s'%(prop_key, func_key),\ 
       property(fget)) 

什么工作是一个函数,它一次创建一个属性,然后从循环中调用该函数。

def __add_secondary_property(self, func , prop_name): 
    fget = lambda self: func(self.__getattribute__(prop_name)) 
    setattr(self.__class__,'%s_%s'%(prop_name,func.__name__),\ 
     property(fget)) 


for prop_name in ['s','z']: 
    for func in [npy.real, npy.imag]: 
     self.__add_secondary_property(func, prop_name) 

回答

1

这可能是因为你叫setattr()self.__class____class__由所有实例共享。如果你修改它,你可以为每个人修改它。尝试setattr(self, ...)

或者,将代码fget更改为在调用实例时查找实例中的值(即稍后有人试图读取该属性时)而不是定义获取者的时间。您在上面的代码中执行的操作是将self.s的当前值复制到共享的getter中(由所有实例共享)。

+0

使用setattr(self,..)返回一个属性类型,而不是实际为父对象创建一个属性 – alex 2012-02-29 17:38:29