python3 高阶函数,装饰器,匿名函数,偏函数

高阶函数

变量可以指向函数,函数的参数能接受变量,那么一个函数可以接受另外一个函数作为参数,这种函数称为高阶函数;

map函数
map()函数接受两个参数,一个是函数,一个是序列,map将传入的函数依次作用到序列的每一个元素,并将新的结果作为list返回;

自定义函数:
def f(x):
    return x*x
序列:l = [1,2,3,4,5]
r = map(f,l)
print(list(r))
输出结果:
[1, 4, 9, 16, 25]
注意:由于结果r是一个迭代器,迭代器是惰性序列,因此通过list()函数让它把整个序列都计算出来并返回一个列表。

reduce函数
reduce函数把一个函数作用在一个序列上,而这个函数必须接受两个参数,reduce函数把结果和序列的下一个元素做累计计算;
reduce(f, [x1, x2, x3, x4]) = f(f(f(x1, x2), x3), x4)

自定义求和函数:
def add(x,y):
    return x+y
#导入reduce函数
from functools import reduce
序列:l = [1,2,3,4,5]
print(reduce(add,l))
输出结果:15
练习:将序列[1,2,3,4,5]转化为整数12345
from functools import reduce
def int1(x,y):
    return x*10+y
l = [1,2,3,4,5]
print(reduce(int1,l))
输出结果:12345

filter函数
filter函数接受一个函数和一个序列。filter函数把传入的函数依次作用于序列的每一个元素,然后根据返回值是true还是false决定保留还是丢弃该元素。

###保留序列的奇数
def is_odd(n):
    return n % 2 == 1
l = [1,2,3,4,5]
print(list(filter(is_odd,l)))
#filter(is_odd,l)函数返回值为一个迭代器,需要用list()函数获得所有结果并返回list。
输出结果:[1, 3, 5]

sorted函数:排序算法

###sorted对于一般的列表进行排序
print(sorted([4,6,8,2,5,1]))
输出结果:[1, 2, 4, 5, 6, 8]

###sorted通过定义key值来进行排序,这里是按照绝对值大小排序
print(sorted([-4,6,-8,2,-5,1],key=abs))
输出结果:[1, 2, -4, -5, 6, -8]

###对字符串的大小排序,默认情况下,对字符串排序,是按照ASCII的大小比较的
print(sorted(['a','b','c','d','Z']))
输出结果:['Z', 'a', 'b', 'c', 'd']

###忽略字符串的大小写进行排序,通过定义key值实现
print(sorted(['a','b','c','d','Z'],key=str.lower))
输出结果:['a', 'b', 'c', 'd', 'Z']

###字符串的反向排序,传递第三个值reverse(反向)为真
print(sorted(['a','b','c','d','Z'],key=str.lower,reverse=True))
输出结果:['Z', 'd', 'c', 'b', 'a']

返回函数
高阶函数除了可以接受函数作为参数外,还可以把函数作为结果值返回。

#自定义函数实现一个可变参数的求和,根据需要再计算求和结果,后期返回求和的函数即可
def lazy_sum(*args):
    def sum():
        ax = 0
        for i in args:
            ax = ax + i
        return ax
    return sum
###调用lazy_sum函数是返回的不是计算结果,而是求和函数;
f = lazy_sum(1,2,3)
print(type(f),f)
输出结果:<class 'function'> <function lazy_sum.<locals>.sum at 0x0000027F3366FD90>
###调用函数f时,返回计算求和的结果:
print(f())
输出结果:6

闭包
注意:返回函数不要引用任何循环变量,或者后续会发生变化的变量

def count():
    fs = []
    for i in range(1,4):
        def f():
            return i*i
        fs.append(f)
    return fs
f1,f2,f3 = count()
print(f1(),f2(),f3())
输出结果:9 9 9
#返回的函数引用了变量i,但它并非立刻执行。等到3个函数都返回时,它们所引用的变量i已经变成了3,返回结果为9

需要调用循环变量:
#创建一个函数,用该函数的参数绑定循环变量当前的值,无论该循环变量后续如何更改,已绑定到函数参数的值不变:
def count():
    def f(j):
        def g():
            return j*j
        return g
    fs = []
    for i in range(1,4):
        fs.append(f(i))
    return fs

f1,f2,f3 = count()
print(f1(),f2(),f3())
输出结果:1 4 9

匿名函数
匿名函数lambda x: x * x:关键字lambda表示匿名函数,冒号前面的x表示函数参数。

###匿名函数赋值给一个变量,再利用变量来调用该函数
m = lambda x: x+x
print(type(m),m)  #查看m变量的格式以及输出值
输出结果:<class 'function'> <function <lambda> at 0x00000280F4DFF9D8>
print(m(5))  #调用变量m
输出结果:10

###匿名函数作为返回值
def hello(x):
   return lambda:x+x

print(hello(4))  #调用该函数,输出结果为函数
输出结果:<function hello.<locals>.<lambda> at 0x0000025F0897FD90>

装饰器
在代码运行期间动态增加功能的方式,称之为“装饰器”(Decorator)
装饰器(Decorator)是一种特殊的函数,用来给函数添上新功能的函数。
主要用于抽离出大量函数中与函数本身无关的雷同代码并继续重用。
装饰器又可分为带参数和不带参数影响原有输出

###装饰器格式
def decorator(fun):
     def wrapper(*args, **kwargs):
         pass
     return wrapper
###使用方法:
 @装饰器名称       
 def hello():
     pass
注意:第一层接收一个函数function,第二层构造一个函数来接收function的参数,然后在内部完成需要添加的功能并正确调用函数,然后在第一层返回第二层构造的这个函数。

示例:
import time
def count_time(func):
    def wrapper(*args,**kwargs):
        start_time = time.time()
        func()
        end_time = time.time()
        print("%s函数执行的时间为:%s"%(func.__name__,end_time-start_time))
    return wrapper
#定义时将hello()函数传递给func()函数,执行wrapper函数;

@count_time
def hello():
    print("hello")
    time.sleep(2)

f = hello() #将hello函数赋值为变量f
print(f) #调用变量f
输出结果:
hello
hello函数执行的时间为:2.0007965564727783
None  #因为heelo()函数没有定义return返回值,返回默认为None

偏函数:
偏函数(Partial function):把一个函数的某些参数给固定住(也就是设置默认值),返回一个新的函数,调用这个新函数会更简单。

#将字符串转化为整形数值,默认进制为10进制
print(int('1234'))
输出结果:1234

#定义函数将10进制改为2进制转化
第一种方法:
def int2(x,base=2):
    return int(x,base)
print(int2('100'))
输出结果:4
第二种方法:
import functools
int2 = functools.partial(int,base=2)
print(int2('100'))
输出结果:4

猜你喜欢

转载自blog.csdn.net/weixin_39249306/article/details/81978147