前言:
Python 的 lambda 表达式是一种匿名函数的快捷方式,它允许你在代码中快速定义单行的小函数。lambda 表达式的语法非常简洁:它仅使用 lambda 关键字 followed by one or more arguments, a colon :, and the expression to evaluate and return. 这使得 lambda 表达式尤其适合于需要函数对象的地方,比如map()、filter()及排序操作等,而不必正式地定义一个函数。
匿名函数,顾名思义,是没有名字的函数。在 Python 中,匿名函数通过 lambda 表达式来创建。
匿名函数不像标准的函数那样用 def 关键字定义,它没有函数名,只有函数体。因此,匿名函数也被称作 lambda 函数。匿名函数通常用于一些只需要临时使用一次的小函数,特别是在需要将函数作为参数传递给高阶函数时。
1 lambda表达式的语法:
lambda arguments: expression
这里,arguments 是传递给 lambda 的参数,可以是多个参数,用逗号隔开;expression 是关于这些参数的表达式,表达式的计算结果会被 lambda 表达式返回。
1.1 例1: 将一个列表中的元素都加上10。
普通函数:
def add_ten(x):
return x + 10
print(add_ten(5)) # 15
lambda 表达式:
add_ten_lambda = lambda x: x + 10
print(add_ten_lambda(5)) # 15
1.2 例2: 使用filter()函数过滤出列表中的偶数。
普通函数:
def is_even(x):
return x % 2 == 0
filtered_even = filter(is_even, [1, 2, 3, 4, 5, 6])
print(list(filtered_even)) # [2, 4, 6]
lambda 表达式:
filtered_even_lambda = filter(lambda x: x % 2 == 0, [1, 2, 3, 4, 5, 6])
print(list(filtered_even_lambda)) # [2, 4, 6]
1.3 使用 map() 和 lambda 表达式来计算每个数字的平方
普通函数:
# 定义原始列表
numbers = [1, 2, 3, 4, 5]
# 定义一个普通函数用于计算数字的平方
def square(x):
return x ** 2
# 使用 map() 和普通函数来计算每个数字的平方
squared_numbers = map(square, numbers)
# 将 map 对象转换为列表并打印
print(list(squared_numbers)) # 输出: [1, 4, 9, 16, 25]
lambda实现:
# 定义原始列表
numbers = [1, 2, 3, 4, 5]
# 使用 map() 和 lambda 表达式来计算每个数字的平方
squared_numbers = map(lambda x: x ** 2, numbers)
# 将 map 对象转换为列表并打印
print(list(squared_numbers)) # 输出: [1, 4, 9, 16, 25]
1.4 多参数举例
比如说我们想要根据一个列表中元组的第二个元素进行排序,可以使用 lambda 表达式作为 sorted() 函数的 key 参数,这里的参数我们也可以传入一个list
普通函数:
# 假设我们有一个元组列表
pair_list = [(1, 'one'), (2, 'two'), (3, 'three'), (4, 'four')]
# 定义一个普通函数,该函数用于获取元组的第二个元素
def get_second_element(pair):
return pair[1]
# 使用普通函数作为排序的键
sorted_list = sorted(pair_list, key=get_second_element)
print(sorted_list)
# 输出:[(4, 'four'), (1, 'one'), (3, 'three'), (2, 'two')]
lambda实现:
# 假设我们有一个元组列表
pair_list = [(1, 'one'), (2, 'two'), (3, 'three'), (4, 'four')]
# 使用 lambda 表达式作为排序的键(根据每个元组的第二个元素)。
sorted_list = sorted(pair_list, key=lambda pair: pair[1])
print(sorted_list)
# 输出:[(4, 'four'), (1, 'one'), (3, 'three'), (2, 'two')]
在这个例子中,lambda pair: pair[1] 指示 sorted() 函数根据元组中索引为 1 的元素(即元组中的字符串)来进行排序。
通过这些例子,可以看到 lambda 表达式是非常灵活的,并能以简洁的方式处理多参数的情况。
1.5 lambda和与普通函数的区别
定义方式: lambda 表达式是匿名的,即没有具体的名称,而普通函数以def关键字定义,拥有函数名。
简洁性: lambda 表达式通常很简短,只能有一个表达式,不像普通函数那样可以包含多行代码。
使用场景: 由于它们的简洁性,lambda 表达式常用于需要简单函数作为参数的场景中,如map()、filter()函数等,而普通函数更适合复杂的逻辑。
返回值: lambda 自动返回其单个表达式的结果,普通函数则需要显式返回值,使用return语句。
1.6 匿名函数的优点:
简洁性: lambda 表达式通常只包含单个表达式,创建时不需要命名,这样可以编写更简洁的代码。
表达式本质: lambda 函数可以在需要函数的任何地方使用,经常用来编写跨越多行的表达式。
无需声明: 直接在需要的地方使用 lambda 表达式,可以避免在全局命名空间添加不必要的函数声明。
作为参数: 常用作其他函数的参数,尤其是在排序、过滤等操作中常作为key函数。
闭包: 它们可以捕获包含作用域的变量(形成闭包),所以它们能访问这些变量,即便离开了变量的作用域。
1.6 匿名函数的缺点:
功能限制: lambda 表达式被设计为直接计算一个表达式的值,不支持多条语句、分支和循环等构造。
可读性: 复杂的 lambda 表达式可读性差,可能会使代码难以理解,特别是对于不熟悉 lambda 的读者。
调试难度: lambda 表达式不容易调试,因为它缺少函数名,导致调试信息不够详细。
文档化: 匿名函数不能够像常规函数那样被单独文档化,因为它们没有名称。
性能: lambda 函数可以在运行时创建,这可能会略微影响性能,特别是在大量使用时。
在实践中,开发者通常在需要简单函数而不想或不需要声明一个完整函数时使用 lambda 表达式。如果一个函数是单次使用,特别是作为另一个函数的参数(比如 map()、filter()、sorted()),而且函数的逻辑足够简单,那么使用 lambda 表达式是很合适的。
然而,当函数的逻辑变得复杂时,或者当相同的函数在多个地方需要被使用时,定义一个具有明确名称和文档的常规函数通常更为合适,这有助于提高代码的可读性和可维护性。
总结:
总的来说,lambda 表达式提供了一种快速定义简单函数的方法,适合用于简单的操作,而普通函数则更适合处理更复杂的任务。