Python高阶函数 - 函数作为参数和返回值
Python高阶函数是指可以接收其他函数作为参数或返回一个函数的函数,这种处理方式在Python中非常常见。这个概念看上去有些奇怪,但是实际上在面向对象编程中也有很多与之类似的现象。高阶函数是Python中的一种常见的编程技巧,可以让程序员更加方便地处理数据和控制程序的执行流程。
一、函数作为参数
Python中可以将函数作为参数传递给其他函数,这种方法可以让我们在调用函数时,更加灵活地定制需要执行的代码。函数作为参数的情况比较多,下面我们会讨论一些常见的应用场景。
1. map()函数 - 将函数作为参数
map()函数是Python内置的一个高阶函数,该函数的作用是将一个函数作用于一个序列(列表或元组等)中的每一个元素。通过函数作为参数的形式,map()函数可以使程序员更加方便地处理序列中每一个元素的值。
map()函数的定义:map(function, iterable)
其中,function参数指定要对iterable中的元素执行的函数,iterable参数指定需要处理的序列。map()函数会返回一个新的序列,该序列中的每个元素都是function()函数对iterable序列中对应元素的处理结果。
例如,我们可以定义一个函数,将列表中的所有元素都加1:
def add_one(x):
return x + 1
lst = [1, 2, 3, 4]
result = map(add_one, lst)
print(list(result)) # [2, 3, 4, 5]
在该例子中,我们将函数add_one(该函数将一个参数加1)传递给了map()函数,使map()函数将add_one()对每个元素进行了处理,并返回了一个新的序列。
2. filter()函数 - 将函数作为参数
filter()函数也是Python内置的一个高阶函数,该函数可以根据函数的返回值来过滤一个序列中的元素。与map()函数非常类似,filter()函数也可以接受一个函数作为参数,并对序列中的每个元素进行处理。
filter()函数的定义:filter(function, iterable)
其中,function参数指定用于过滤iterable的函数,iterable参数指定需要处理的序列。filter()函数会返回一个新的序列,该序列中的元素都是function()函数返回True的那些元素。
例如,我们可以定义一个函数,用于判断一个数是否为偶数:
def is_even(x):
return x % 2 == 0
lst = [1, 2, 3, 4]
result = filter(is_even, lst)
print(list(result)) # [2, 4]
在该例子中,我们将函数is_even(该函数检查一个数是否为偶数)传递给了filter()函数,使filter()函数只返回了lst序列中所有偶数元素。
3. reduce()函数 - 将函数作为参数
reduce()函数也是Python内置的一个高阶函数,该函数可以对一个序列中的元素进行迭代运算。与map()函数和filter()函数不同,reduce()函数传入的参数有两个:一个是处理函数(一定要有两个参数),一个是序列。reduce()函数的执行流程如下:
1. 首先将序列 、第二个元素传给处理函数进行运算,返回的结果作为下一次运算的 个参数。
2. 将刚才运算结果与序列中第三个元素传给处理函数进行运算,返回的结果作为下一次运算的 个参数。
3. 重复上述步骤,最终返回处理函数对序列中所有元素的迭代运算结果。
例如,我们可以使用reduce()函数计算列表中所有元素的和:
from functools import reduce
def add(a, b):
return a + b
lst = [1, 2, 3, 4]
result = reduce(add, lst)
print(result) # 10
在该例子中,我们定义了add()函数,用于对两个元素进行加和运算,并将该函数传递给reduce()函数。由于lst中有4个元素,reduce()函数会将 个元素和第二个元素传递给add()函数进行运算,得到结果3;然后将3和第3个元素传递给add()函数进行运算,得到结果6;最后将6和第4个元素传递给add()函数进行运算,得到结果10,因此,reduce()函数返回的结果为10。
二、函数作为返回值
Python中可以将函数作为返回值。这种方法可以在需要时返回一个具体的函数,使程序员更加方便地执行所需的操作。以下是一些常见的应用场景。
1. 闭包 - 返回一个函数
闭包是Python中常用的一种函数类型,它允许一个函数返回一个函数,并保存外部函数的变量状态。这种情况下,返回的函数可以访问外部函数的变量,并且这些变量的状态会在外部函数调用后保持不变。
例如,我们可以定义一个函数,用于返回另一个函数,实现加法计算功能:
def calculate(a):
def add(b):
return a + b
return add
result = calculate(5)
print(result(3)) # 8
在该例子中,我们定义了calculate()函数,该函数返回了一个add()函数。由于calculate()函数中传入了参数5,因此返回的add()函数中可以访问到变量a的值,当我们调用result(3)时,add()函数会将5和3相加,并返回结果8。
2. 装饰器 - 返回一个函数
装饰器是Python中常见的一种函数类型,用于扩展一个函数的功能。装饰器可以接收一个函数作为参数,并返回一个新的函数(通常也是一个函数),该函数具备原始函数的所有功能,并且还具备一些额外的功能。
例如,我们可以定义一个装饰器,用于使一个函数能够记录程序执行时间:
import time
def run_time(func):
def wrapper(*args, **kwargs):
start_time = time.time()
result = func(*args, **kwargs)
end_time = time.time()
print("Running time:", end_time - start_time)
return result
return wrapper
@run_time
def add(a, b):
time.sleep(1)
return a + b
print(add(1, 2)) # Running time: 1.000166654586792
# 3
在该例子中,我们定义了一个run_time()装饰器,用于记录函数执行时间。该装饰器接收一个函数作为参数,返回一个新的函数wrapper。当我们在函数定义时使用@run_time装饰器时,会自动将该函数传递给run_time()装饰器,并将返回的wrapper函数。在运行add()函数时,由于该函数有被@run_time装饰器修饰,因此会先运行wrapper()函数,记录程序执行时间,并返回add()函数的执行结果。所以,我们在运行print(add(1, 2))时,会得到1秒的运行时间和结果3。
总结:
以上是介绍Python高阶函数中函数作为参数和返回值的应用场景,这些例子说明Python高阶函数非常灵活,可以根据需求对函数进行更加精细的操作,提高程序的效率和可维护性。掌握高阶函数的应用场景,可以让程序员更加便捷地实现自己的业务优化和逻辑设计。
