python偏函数
https://zhuanlan.zhihu.com/p/47124891
和装饰器一样,它可以扩展函数的功能,但又不完成等价于装饰器。通常应用的场景是当我们要频繁调用某个函数时,其中某些参数是已知的固定值,通常我们可以调用这个函数多次,
但这样看上去似乎代码有些冗余,而偏函数的出现就是为了很少的解决这一个问题。举一个很简单的例子,比如我就想知道 100 加任意数的和是多少,通常我们的实现方式是这样的:
# 第一种做法:
def add(*args):
return sum(args)
print(add(1, 2, 3) + 100)
print(add(5, 5, 5) + 100)
# 第二种做法
def add(*args):
# 对传入的数值相加后,再加上100返回
return sum(args) + 100
print(add(1, 2, 3)) # 106
print(add(5, 5, 5)) # 115
看上面的代码,貌似也挺简单,也不是很费劲。但两种做法都会存在有问题:
第一种,100这个固定值会返回出现,代码总感觉有重复;
第二种,就是当我们想要修改 100 这个固定值的时候,我们需要改动 add 这个方法。下面我们来看下用 parital 怎么实现:
from functools import partial
def add(*args):
return sum(args)
add_100 = partial(add, 100)
print(add_100(1, 2, 3)) # 106
add_101 = partial(add, 101)
print(add_101(1, 2, 3)) # 107
参数:
func: 需要被扩展的函数,返回的函数其实是一个类 func 的函数
*args: 需要被固定的位置参数
**kwargs: 需要被固定的关键字参数 # 如果在原来的函数 func 中关键字不存在,将会扩展,如果存在,则会覆盖
- 理解代码
# 同样是刚刚求和的代码,不同的是加入的关键字参数
def add(*args, **kwargs):
# 打印位置参数
for n in args:
print(n)
print("-"*20)
# 打印关键字参数
for k, v in kwargs.items():
print('%s:%s' % (k, v))
# 暂不做返回,只看下参数效果,理解 partial 用法
# 普通调用
add(1, 2, 3, v1=10, v2=20)
"""
1
2
3
--------------------
v1:10
v2:20
"""
# partial
add_partial = partial(add, 10, k1=10, k2=20)
add_partial(1, 2, 3, k3=20)
"""
10
1
2
3
--------------------
k1:10
k2:20
k3:20
"""
add_partial(1, 2, 3, k1=20)
"""
10
1
2
3
--------------------
k1:20
k2:20
"""
- 应用代码
from functools import partial
basetwo = partial(int, base=2)
basetwo.__doc__ = 'Convert base 2 string to an int.'
res = basetwo('10')
print(res) # 2
print(int('10',base=2)) # 2
- partial实现代码类似如下:
def partial(func, *args, **keywords):
def newfunc(*fargs, **fkeywords):
newkeywords = keywords.copy()
newkeywords.update(fkeywords)
return func(*args, *fargs, **newkeywords)
return newfunc