Differences between revisions 1 and 3 (spanning 2 versions)
Revision 1 as of 2005-06-28 05:42:17
Size: 2771
Editor: LiJie
Comment:
Revision 3 as of 2005-06-28 05:56:17
Size: 2429
Editor: LiJie
Comment:
Deletions are marked like this. Additions are marked like this.
Line 4: Line 4:
#!python
Line 5: Line 6:
     def __init__(self, *calls, **opts):
                for call in calls:
                        if not callable(call):
                
raise RuntimeError, str(call) + ' not a callable object'
                self.calls = () + calls
                self.emptyExcept = opts.get('emptyExcept', False)
        def __call__(self, *args):
                if self.emptyExcept and not self.calls:
             raise RuntimeError, 'No callable objects'
    def __init__(self, *calls, **opts):
        for call in calls:
            if not callable(call):
raise RuntimeError, str(call) + ' not a callable object'
        self.calls = () + calls
        self.emptyExcept = opts.get('emptyExcept', False)
    def __call__(self, *args):
        if self.emptyExcept and not self.calls:
            raise RuntimeError, 'No callable objects'
Line 15: Line 16:
         try:
                        result = None
             for call in self.calls:
                                result = call (*args)
                        return result
        
except TypeError:
                        raise RuntimeError, 'Invalid callable type: ' + str(call)
        try:
            result = None
            for call in self.calls:
                result = call (*args)
            return result
except TypeError:
            raise RuntimeError, 'Invalid callable type: ' + str(call)
Line 23: Line 24:
     def __add__(self, call):
                if not callable(call):
             raise RuntimeError, str(call) + ' not a callable object'
                return delegate(*(self.calls + (call,)))
        def __iadd__(self, *calls):
         self.calls += calls
                return self
    def __add__(self, call):
        if not callable(call):
            raise RuntimeError, str(call) + ' not a callable object'
        return delegate(*(self.calls + (call,)))
    def __iadd__(self, *calls):
        self.calls += calls
        return self
Line 33: Line 34:
     def a(v1, v2):
         print 'a:', v1, v2
        def b(v1, v2):
         print 'b:', v1, v2
        def c(v1, v2):
         print 'c:', v1, v2
    def a(v1, v2):
        print 'a:', v1, v2
    def b(v1, v2):
        print 'b:', v1, v2
    def c(v1, v2):
        print 'c:', v1, v2
Line 40: Line 41:
     class Test:
         def hello(self, v1, v2):
                        print 'Test.hello:', v1, v2
    class Test:
        def hello(self, v1, v2):
            print 'Test.hello:', v1, v2
Line 44: Line 45:
     class Test1:
         def __call__(self, v1, v2):
                        print 'Test1.__call__:', v1, v2
    class Test1:
        def __call__(self, v1, v2):
            print 'Test1.__call__:', v1, v2
Line 48: Line 49:
     print '======== test delegate.__init__ and delegate.__call__'
        f = delegate(a, b, c, Test().hello, Test1())
        f (3, 4)
        print '======== test delegate.__add__'
        f1 = f + a
        f1 (5, 6)
        print '======== test delegate.__iadd__'
        f2 = delegate(a, b)
        f2 += c
        f2 (9, 10)
        print '======== test delegate.__call__ return value'
     f3 = delegate(lambda x, y: x*y)
        assert f3(10, 11) == 10*11
        f3 = delegate(lambda x, y: x*y, lambda x, y: x**y)
    print '======== test delegate.__init__ and delegate.__call__'
    f = delegate(a, b, c, Test().hello, Test1())
    f (3, 4)
    print '======== test delegate.__add__'
    f1 = f + a
    f1 (5, 6)
    print '======== test delegate.__iadd__'
    f2 = delegate(a, b)
    f2 += c
    f2 (9, 10)
    print '======== test delegate.__call__ return value'
    f3 = delegate(lambda x, y: x*y)
    assert f3(10, 11) == 10*11
    f3 = delegate(lambda x, y: x*y, lambda x, y: x**y)

完成了一般的委托功能,一个委托上挂多个函数,可以设置函数列表为空时,是否抛出异常。返回值是函数列表中最后一个函数调用的返回,使用方法可参见test部分。

   1 class delegate:
   2     def __init__(self, *calls, **opts):
   3         for call in calls:
   4             if not callable(call):
   5                 raise RuntimeError, str(call) + ' not a callable object'
   6         self.calls = () + calls
   7         self.emptyExcept = opts.get('emptyExcept', False)
   8     def __call__(self, *args):
   9         if self.emptyExcept and not self.calls:
  10             raise RuntimeError, 'No callable objects'
  11 
  12         try:
  13             result = None
  14             for call in self.calls:
  15                 result = call (*args)
  16             return result
  17         except TypeError:
  18             raise RuntimeError, 'Invalid callable type: ' + str(call)
  19 
  20     def __add__(self, call):
  21         if not callable(call):
  22             raise RuntimeError, str(call) + ' not a callable object'
  23         return delegate(*(self.calls + (call,)))
  24     def __iadd__(self, *calls):
  25         self.calls += calls
  26         return self
  27 
  28 
  29 if __name__ == '__main__':
  30     def a(v1, v2):
  31         print 'a:', v1, v2
  32     def b(v1, v2):
  33         print 'b:', v1, v2
  34     def c(v1, v2):
  35         print 'c:', v1, v2
  36 
  37     class Test:
  38         def hello(self, v1, v2):
  39             print 'Test.hello:', v1, v2
  40 
  41     class Test1:
  42         def __call__(self, v1, v2):
  43             print 'Test1.__call__:', v1, v2
  44 
  45     print '======== test delegate.__init__ and delegate.__call__'
  46     f = delegate(a, b, c, Test().hello, Test1())
  47     f (3, 4)
  48     print '======== test delegate.__add__'
  49     f1 = f + a
  50     f1 (5, 6)
  51     print '======== test delegate.__iadd__'
  52     f2 = delegate(a, b)
  53     f2 += c
  54     f2 (9, 10)
  55     print '======== test delegate.__call__ return value'
  56     f3 = delegate(lambda x, y: x*y)
  57     assert f3(10, 11) == 10*11
  58     f3 = delegate(lambda x, y: x*y, lambda x, y: x**y)
  59         assert f3(10, 11) == 10**11
  60         print '======== test delegate.__call__ with empty exception (empty)'
  61         f4 = delegate (emptyExcept=True)
  62         try:
  63                 f4 (3, 5)
  64         except RuntimeError, ex:
  65                 print 'Exception:', ex
  66         print '======== test delegate.__call__ with empty exception (not empty)'
  67         f4 += a
  68         f4 (3, 5)

PythonDelegate (last edited 2009-12-25 07:09:16 by localhost)