您的位置:首页 > 编程语言 > Python开发

Learning Python 012 函数式编程 2 返回函数 匿名函数 装饰器 偏函数

2016-07-23 20:51 741 查看

Python 函数式编程 2

返回函数

返回函数的意思就是:函数作为返回值。(高阶函数除了可以接受函数作为参数外,还可以把函数作为结果值返回。)

举个例子:实现一个可变参数的求和。

正常的函数:

def calc_sum(*args):
ax = 0
for n in args:
ax = ax + n
return ax


返回函数的函数,其实和上面的函数很像:

def lazy_sum(*args):
def sum():
ax = 0
for n in args:
ax = ax + n
return ax
return sum


调用
lazy_sum()
时,返回的并不是求和结果,而是求和函数:

>>> f = lazy_sum(1, 3, 5, 7, 9)
>>> f
<function lazy_sum.<locals>.sum at 0x101c6ed90>


调用函数
f()
时,才真正计算求和的结果:

>>> f()
25


lazy_sum
返回函数
sum
时,相关参数和变量都保存在返回的函数中,这种称为“闭包Closure)”的程序结构拥有极大的威力。

要注意:调用
lazy_sum()
时,每次调用都会返回一个新的函数,即使传入相同的参数,得到的两个返回函数也不是一样的:

>>> f1 = lazy_sum(1, 3, 5, 7, 9)
>>> f2 = lazy_sum(1, 3, 5, 7, 9)
>>> f1==f2
False


参考网站:

https://www.zhihu.com/question/20125256

匿名函数

匿名函数就是带有
lambda
关键字的公式。

比如函数:

def f(x):
return x * x


可以写成匿名函数的样子:

>>> f = lambda x: x * x


使用匿名函数

>>> f
<function <lambda> at 0x101c6ef28>
>>> f(5)
25


同样,也可以把匿名函数作为返回值返回:

def build(x, y):
return lambda: x * x + y * y


装饰器

>>> def now():
...     print('2015-3-25')
...
>>> now()
2015-3-25


函数对象有一个
__name__
属性,可以拿到函数的名字

>>> now.__name__
'now'


在代码运行期间动态增加功能的方式,称之为“装饰器”(Decorator)。decorator就是一个返回函数高阶函数

举例,我们来定义一个能打印日志的decorator

def log(func):
def wrapper(*args, **kw):
print('call %s():' % func.__name__)
return func(*args, **kw)
return wrapper


decorator置于函数的定义处:

@log
def now():
print('2015-3-25')


现在再调用
now()
函数:

>>> now()
call now():
2015-3-25


看到了吧,
call now():
就是
log
装饰器输出的信息。

@log
放到
now()
函数的定义处,相当于执行了语句:

now = log(now)


偏函数

偏函数就是:举例:

假设要转换大量的二进制字符串,每次都传入
int(x, base=2)
非常麻烦,于是,我们想到,可以定义一个
int2()
的函数,默认把
base=2
传进去:

def int2(x, base=2):
return int(x, base)


这样运行
int2()


>>> int2('1000000')
64
>>> int2('1010101')
85


这个
int2()
函数就叫做:偏函数

functools.partial
就是帮助我们创建一个偏函数的,不需要我们自己定义
int2()


>>> import functools
>>> int2 = functools.partial(int, base=2)
>>> int2('1000000')
64


functools.partial
的作用就是,把一个函数的某些参数给固定住(也就是设置默认值),返回一个新的函数。

再举个例子:

max2 = functools.partial(max, 10)


实际上会把
10
作为
*args
的一部分自动加到左边,也就是:

max2(5, 6, 7)


相当于:

args = (10, 5, 6, 7)
max(*args)


参考网站:

http://www.liaoxuefeng.com/wiki/0014316089557264a6b348958f449949df42a6d3a2e542c000/0014317848428125ae6aa24068b4c50a7e71501ab275d52000

http://www.liaoxuefeng.com/wiki/0014316089557264a6b348958f449949df42a6d3a2e542c000/00143184474383175eeea92a8b0439fab7b392a8a32f8fa000
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息