Python - 如果函数是第一类对象,函数是否可以有方法?

时间:2014-01-13 17:28:28

标签: python function reflection metaprogramming

我有一个维护功能列表的类。这些函数只是坐在队列中的对象,并且每次都会弹出一个并执行它。但是,有时我想打印出这个列表,我想象的代码如下:

for function in self.control_queue:
    print function.summarize()
    if function.ready():
        function()

换句话说,我想在这些函数对象上调用我想在某处定义的summarize()ready()方法。此外,我希望能够在此队列上抛出匿名函数 - 即动态生成所有内容。

3 个答案:

答案 0 :(得分:1)

你可以把它变成一个类并定义__call__

class MyClass():
    def summarize(self):
        #summarize stuff
        pass

    def ready(self):
        #ready stuff
        pass

    def _call__(self):
        #put the code here, for when you call myClass()
        pass

你如何运行它:

function = MyClass()
print function.summarize()
if function.ready():
    function()

答案 1 :(得分:1)

你有几种可能的方法。

您可以将定义添加到函数中。

def foo():
    pass
# later..
foo.summarize = lambda: "To pair with bar"
foo.ready = lambda: True

您可以创建类对象来包装函数操作。

class Func():
    def summarize(self):
        return "Function!"

    def ready(self):
        return self.ready

    def __call__(self):
        # Act as a function

或者您可以使用一个功能来检查这些功能的功能标签。

def summarize_func(func):
    return func.__name__ # Or branch here on specific names/attributes

def ready_func(func):
    return True # Or branch on names/attributes

最后,为了适应匿名函数,您可以检查这些属性的预见性,并在缺少属性时乐观地返回。然后,您可以将上述方法与可用于任何函数的方法结合起来。

def summarize_func(func):
    if hasattr(func, summarize):
        return func.summarize()
    else:
        # Note this will just be '<lambda>' for anonymous funcs
        return func.__name__

def ready_func(func):
    if hasattr(func, ready):
        return func.ready()
    else:
        return True

答案 2 :(得分:0)

一个选项是将函数实现为类实例:

class Function(object):
     def summarize(self): pass # some relevant code here
     def __call__(self): pass  #    and there

稍后使用

function = Function()

实施__call__ magic method后,此function成为可调用对象。

当然,您可以为函数指定属性,但它相当模糊且具有直观性:

>>> def summ(a): return sum(a)
...
>>> def function(a): return a
...
>>> function.sum=summ
>>> function.sum([1,2,3])
6