利用metaclass實現python的aop

修行Python個把星期,終於有點成果了,呵呵,一個利用metaclass實現的aop。

其實python這類非常動態的語言要實現AOP是很容易的,所以首先我們要來先定義一個metaclass

然後我們要在__new__()這個metaclass 的時候動態植入方法到要調用地方法的前後。

具體代碼如下:

class pyaop(type):
    '''
    這個空方法是用來將後面的beforeop和afterop初始化成函數引用
    '''
    def nop(self):
        pass
    '''
    下面這兩個變量是類變量,也就是存放我們要植入的兩個函數的地址的變量
    '''
    beforeop=nop
    afterop=nop
    '''
    設置前後兩個植入函數的類函數
    '''
    @classmethod
    def setbefore(self,func):
        pyaop.beforeop=func
    @classmethod
    def setafter(self,func):
        pyaop.afterop=func
    '''
    初始化metaclass的函數,這個函數最重要的就是第四個參數,dict通過這個參數我們可以修改類的屬性(方法)
    '''
    def __new__(mcl,name,bases,dict):
        from types import FunctionType #加載類型模塊的FunctionType
        obj=object() #定義一個空對象的變量
        '''
        這個就是要植入的方法,func參數就是我們要調用的函數
        '''
        def aop(func):
            '''
            我們用這個函數來代替將要調用的函數
            '''
            def wrapper(*args, **kwds):
                pyaop.beforeop(obj) #調用前置函數
                value = func(*args, **kwds) #調用本來要調用的函數
                pyaop.afterop(obj) #調用後置函數
                return value #返回
            return wrapper
        #在類的成員列表中查找即將調用的函數
        for attr, value in dict.iteritems():
            if isinstance(value, FunctionType):
                dict[attr] = aop(value) #找到後用aop這個函數替換之
        obj=super(pyaop, mcl).__new__(mcl, name, bases, dict) #調用父類的__new__()創建self
        return obj
class A(object):
    __metaclass__ = pyaop
    def foo(self):
        total = 0
        for i in range(100000):
            total = total+1
        print total
 
    def foo2(self):
        from time import sleep
        total = 0
        for i in range(100000):
            total = total+1
            sleep(0.0001)
        print total
def beforep(self):
    print('before')
def afterp(self):
    print('after')

if __name__ == "__main__":
    pyaop.setbefore(beforep)
    pyaop.setafter(afterp)
    a=A()
    a.foo()
    a.foo2()

轉自:http://www.cnblogs.com/Alexander-Lee/archive/2008/12/06/pythonaop.html
發佈了79 篇原創文章 · 獲贊 38 · 訪問量 144萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章