Python:基于其他类动态创建方法

时间:2011-11-16 13:32:37

标签: python methods dynamic

我已经找了很长时间但找不到我问题的正确答案: 我有一个包含对数组进行操作的方法的类,我希望在另一个具有修改输出的类中动态创建具有相似名称的方法。

到目前为止,我有类似的东西,有人可以指导我吗?

感谢

Class A():

    def__init__(self,array):
        self.data = array

    def method1(self,*args):
        newarray = whatever(self.data,*args)
        return newarray

    def method2(self,*args):
        newarray = whatever2(self.data,*args)
        return newarray

我希望能够使用这些方法在更复杂的类中生成新方法,例如:

class B(C):    #inherits from C

    def __init__(self,[arg1,array]):
        #initialize from parent class
        C.__init__(self,[arg1,array])

        #create new methods for this class using same name
        methodnames = [element for element in dir(A) if element[0] != '_']

        for methodname in methodnames:
            ##following works but this is not the output I want here
            #self.__dict__[methodname] = getattr(A(array),methodname)

            #following doesn't work... at least not as I expect it to
            #case1
            #self.__dict__[methodname] = [arg1,getattr(A(array),methodname)]
            #case2
            self.__dict__[methodname] = list([arg1,getattr(A(array),methodname)])

a = array
#following returns a list of [arg1, method] but what I really want is [arg1,newarray]
C([arg1,array]).method1(*args)

好的,让我们试着更清楚一点:

A类包含过滤器,接受数组并应用过滤器作为方法,返回过滤后的数据。

类过滤器()

def__init__(self,array):
    self.data = array

def filter1(self,*args):
    newarray = median(self.data,*args)
    return newarray

def filter2(self,*args):
    newarray = gaussian(self.data,*args)
    return newarray

...

在另一个模块中,我有类SpecialData,它在x,y数据列表上运行(其中x和y是可迭代的,即列表,数组......)。像

这样的东西

Class SpecialData():

def __init__(self,[x,y]):
    self.data = [x,y]

def power(self,power):
    ypow = self.data[1]**power
    return [x,pow]

def porod(self):
    return [x**4,x**4*y]

....

现在,我想要的是将类过滤器中包含的过滤器方法添加到SpecialData类中。 当然,我可以通过使用适当格式的SpecialClass重新编码所有过滤器来实现这一点。但我真正想要的是,每次将新过滤器添加到类过滤器时,都要在运行时在SpecialData类中使用它,而不必重新编写新过滤器的代码。

所以,不是很聪明,我试图通过以下方式阅读类过滤器中的可用过滤器列表:

导入过滤器

filternames = [如果元素[0]!='_'的元素在dir(过滤器)中的元素

for filternames中的fitlername:     generate_filters_in_class_SpecialClass

我该如何正确地做到这一点?

我发现了一些与此相关的帖子,一些使用super(),另一些使用SpecialData。 dict 甚至是setattr。由于第二个看起来对我来说更容易理解,所以我专注于这个并提出了:

导入过滤器

Class SpecialData():

def __init__(self,[x,y]):
    self.data = [x,y]

    filternames = [element for element in dir(filters) if element[0] != '_']

    for fitlername in filternames:

        self.__dict__[fitlername ] = [self.data[0],getattr(filters(self.data[1]),fitlername)]

当然,这不起作用,因为列表不可调用。如果我将最后一行更改为: self。 dict [fitlername] = list([self.data [0],getattr(filters(self.data [1]),fitlername)]) 它将方法作为第二个元素返回,而不是结果。

请注意以下作品,但这不是我想要的...... self。 dict [fitlername] = getattr(filters(self.data [1]),fitlername)

希望现在更清楚......

2 个答案:

答案 0 :(得分:1)

我认为你试图在不使用/了解其高级功能的情况下高级使用Python,就像借用其他语言的技术一样。

这不是批评,但您应该查看Python tutorialPython introspectionmetaclasses

我认为,如果您只是完成Python functions的知识,您将能够以更简单的方式轻松解决问题。

答案 1 :(得分:0)

您应该更清楚地了解您要实现的目标,而不是生成建议的解决方案。 A类是起点的明显例子;请发布您想要的终点的例子,例如

Class B(): 

    def__init__(self,array): 
        self.data = array 

    def method1(self,*args): 
        newarray = ComplexWhatever(self.data,*args) 
        return newarray 

    def method2(self,*args): 
        newarray = EvenBiggerWhatever2(self.data,*args) 
        return newarray 

a = A(input_array)
b = B(input_array)
print(a.method1(args))
print(b.method1(args))

不清楚的是你想如何“动态生成”新函数“ComplexWhatever()”而不是手工编写函数。