是否可以从功能类型扩展? (Python 2.7)

时间:2015-09-18 16:18:30

标签: python function python-2.7 operator-overloading

作为我自己的练习,我试图在Python中编写一个与C#中的事件类似的类。

以下是类中的两个主要函数(__subs是一个列表):

class Event (object):
    def __iadd__ (self, other):
        if not callable(other):
            raise ValueError("%s must be callable" % other)
        self.__subs.append(other)
        return self

    def __add__ (self, other):
        if not callable(other):
            raise ValueError("%s must be callable" % other)
        new = Event()
        new.__subs = [f for f in self.__subs]
        new.__subs.append(other)
        return new

    def __call__ (self, *args, **kwargs):
        for func in self.__subs:
            func(*args, **kwargs)

这允许以下语法:

e1 = Event()
e1 += afunction
e2 += another
e1 (arg1, arg = val) # afunction and another will be called with arg1 and val

e2 = Event() + afunction + another
e2 (arg1, arg = val)

(Event() + afunction + another) (arg1, arg = val)

但是,我想简化最后两个就是这样的

e = afunction + another
e (arg1, arg = val)

(afunction + another) (arg1, arg = val)

我尝试过这样做,但是我收到了错误" TypeError:' function'不是可接受的基本类型"

class function (FunctionType):
    def __add__ (self, other):
        return Event() + self + other

我正在尝试做什么?

1 个答案:

答案 0 :(得分:2)

你不能直接将函数子类化,没有。最多可以创建一个包装类,它将所有属性访问传递给底层函数。

要支持调用,请为包装类指定object.__call__ method

class FunctionWrapper(object):
    def __init__(self, func):
        self._func = func

    def __getattr__(self, attr):
        return getattr(self._func, attr)

    def __call__(self, *args, **kwargs):
        return self._func(*args, **kwargs)

    # additional methods

你可以画画'使用装饰器语法进行函数声明甚至:

@FunctionWrapper
def foo(): pass

演示:

>>> @FunctionWrapper
... def foo():
...     return 'bar'
... 
>>> foo
<__main__.FunctionWrapper object at 0x102544850>
>>> foo()
'bar'
>>> foo.__name__
'foo'
>>> foo.__code__
<code object foo at 0x1026cb730, file "<stdin>", line 1>