functools模块包含能够创建高阶函数,函数式编程和装饰器的函数和装饰器
partial
partial(function [,*args [,**kwargs]])
创建一个类似函数的对象partial,当调用该对象时,会使用参数来调用函数function
例:
#!/usr/bin/python3 # -*- coding:utf-8 -*- import functools def add(m,n): print(m+n) if __name__=="__main__": f = functools.partial(add,m=3) for i in range(5): f(n=i)
结果:
3 4 5 6 7
在使用partial对象提到常规函数时,得到的结果与使用常规函数的结果不不完全一致。例如,在类定义中使用partial(),那么该函数的行为类似于静态方法,而不是实例方法
reduce
reduce(function, items [, inital])
向可迭代的items中的项渐增地应用函数function,并返回一个值。
例:
#!/usr/bin/python3 # -*- coding:utf-8 -*- import functools def add(m,n): return m+n if __name__=="__main__": f = functools.reduce(add, [1,2,3,4],5) print(f)
结果:
15
update_wrapper
update_wrapper(wrapper, wrapped [, assigned [, updated]])
这是一个使用工具函数,在编写装饰器的时很有用,将函数wrapped的属性赋值到包装饰器函数wrapper,使包装的函数类似于原始函数。assigned是要复制的属性元组,默认设置为(‘__name__’,'__module__','__doc__')。
updated是一个元组,包含一些函数属性名称,这些函数属性时字典并且需要将它们的值合并到包装器中,默认情况下是('__dict__')
#!/usr/bin/python3 # -*- coding:utf-8 -*- def wrap(func): def call_it(*args,**kwargs): """wrap func: call_it""" print('before call') return func(*args,**kwargs) return call_it @wrap def hello(): """say hello""" print("hello world") from functools import update_wrapper def wrap2(func): def call_it(*args, **kwargs): """wrap func: call_it2""" print('before call') return func(*args, **kwargs) return update_wrapper(call_it, func) @wrap2 def hello2(): """test hello""" print('hello world2') if __name__ == '__main__': hello() print(hello.__name__) print(hello.__doc__) print() hello2() print(hello2.__name__) print(hello2.__doc__)
结果:
before call hello world call_it wrap func: call_it before call hello world2 hello2 test hello
wraps
wraps(function [, assigned [, updated]])
一个装饰器,在它所应用的函数上执行于update.wrapper()相同的任务
例:未使用wraps装饰器
def aaa(func): def bbb(*args, **kwargs): print("****************************") func(*args, **kwargs) print("****************************") return bbb @aaa def ccc(): print("aaaaaaaaaaaaaaaaaaaaaaaaaaa") if __name__ == '__main__': ccc() print(ccc.__name__)
结果:
**************************** aaaaaaaaaaaaaaaaaaaaaaaaaaa **************************** bbb # 函数ccc的__name__打印为bbb
使用wraps装饰器
from functools import wraps def aaa(func): @wraps(func) def bbb(*args, **kwargs): print("****************************") func(*args, **kwargs) print("****************************") return bbb @aaa def ccc(): print("aaaaaaaaaaaaaaaaaaaaaaaaaaa") if __name__ == '__main__': ccc() print(ccc.__name__)
结果:
**************************** aaaaaaaaaaaaaaaaaaaaaaaaaaa **************************** ccc #函数ccc的__name__打印为ccc