标签:返回 int dict get ted 封装 作用 技术 this
转自:http://www.cnblogs.com/xybaby/p/6274187.html
# -*- coding: utf-8 -*- 2 def log_cost_time(func): 3 def wrapped(*args, **kwargs): 4 import time 5 begin = time.time() 6 try: 7 return func(*args, **kwargs) 8 finally: 9 print ‘func %s cost %s‘ % (func.__name__, time.time() - begin) 10 return wrapped 11 12 @log_cost_time 13 def complex_func(num): 14 ret = 0 15 for i in xrange(num): 16 ret += i * i 17 return ret 18 #complex_func = log_cost_time(complex_func) 19 20 if __name__ == ‘__main__‘: 21 print complex_func(100000) 复制代码
代码中,函数log_cost_time就是一个装饰器,其作用也很简单,打印被装饰函数运行时间。
1 @dec 2 def func():pass
本质上等同于: func = dec(func)。
functools.
update_wrapper
(wrapper, wrapped[, assigned][, updated])
This is a convenience function for invoking partial(update_wrapper,wrapped=wrapped,assigned=assigned,updated=updated) as a function decorator when defining a wrapper function.
简单改改代码:
1 import functools 2 def log_cost_time(func): 3 @functools.wraps(func) 4 def wrapped(*args, **kwargs): 5 import time 6 begin = time.time() 7 try: 8 return func(*args, **kwargs) 9 finally: 10 print ‘func %s cost %s‘ % (func.__name__, time.time() - begin) 11 return wrapped
再查看complex_func.__name__ 输出就是 “complex_func”
1 def log_cost_time(stream): 2 def inner_dec(func): 3 def wrapped(*args, **kwargs): 4 import time 5 begin = time.time() 6 try: 7 return func(*args, **kwargs) 8 finally: 9 stream.write(‘func %s cost %s \n‘ % (func.__name__, time.time() - begin)) 10 return wrapped 11 return inner_dec 12 13 import sys 14 @log_cost_time(sys.stdout) 15 def complex_func(num): 16 ret = 0 17 for i in xrange(num): 18 ret += i * i 19 return ret 20 21 if __name__ == ‘__main__‘: 22 print complex_func(100000)
log_cost_time函数也接受一个参数,该参数用来指定信息的输出流,对于带参数的decorator
1 def Haha(clz): 2 clz.__str__ = lambda s: "Haha" 3 return clz 4 5 @Haha 6 class Widget(object): 7 ‘‘‘ class Widget ‘‘‘ 8 9 if __name__ == ‘__main__‘: 10 w = Widget() 11 print w
那什么场景下有必要使用decorator呢,设计模式中有一个模式也叫装饰器。我们先简单回顾一下设计模式中的装饰器模式,简单的一句话概述
动态地为某个对象增加额外的责任
由于装饰器模式仅从外部改变组件,因此组件无需对它的装饰有任何了解;也就是说,这些装饰对该组件是透明的。
回到Python中来,用decorator语法实现装饰器模式是很自然的,比如文中的示例代码,在不改变被装饰对象的同时增加了记录函数执行时间的额外功能。当然,由于Python语言的灵活性,decorator是可以修改被装饰的对象的(比如装饰类的例子)。decorator在python中用途非常广泛,下面列举几个方面:
def catchall(func): @functools.wraps(func) def wrapped(*args, **kwargs): try: return func(*args, **kwargs) except: pass return wrapped
标签:返回 int dict get ted 封装 作用 技术 this
原文地址:http://www.cnblogs.com/zhongguiyao/p/7208432.html