Lambda表达式

C++ Lambda 表达式

C++ 的 Lambda 表达式 是一种轻量级的 匿名函数,用于临时定义函数对象,常用于算法、回调、并发、事件响应等场景。

Lambda 表达式是定义内联函数的简洁方式,允许捕获外部变量,并在需要函数对象的地方直接使用。


一、基本语法

[capture](parameter_list) -> return_type { body }

各部分含义如下:

部分 含义
[] 捕获列表(capture)
() 参数列表
-> 返回值类型(可省略)
{} 函数体

二、基础例子

auto add = [](int a, int b) { return a + b; };
std::cout << add(3, 4);  // 输出 7

也可以直接传给函数:

std::vector<int> v = {1, 2, 3};
std::for_each(v.begin(), v.end(), [](int x) {
    std::cout << x << " ";
});

三、捕获列表(最关键)

1. 按值捕获(copy)

int x = 10;
auto f = [x]() { std::cout << x << std::endl; };

2. 按引用捕获(reference)

int x = 10;
auto f = [&x]() { x += 1; };

3. 捕获所有变量

捕获方式 含义
[=] 捕获所有外部变量的副本(按值)
[&] 捕获所有外部变量引用(按引用)
[=, &y] 所有按值,但 y 按引用
[&, x] 所有按引用,但 x 按值

四、结合 STL 使用(常用)

std::vector<int> v = {1, 2, 3, 4};
int threshold = 2;

v.erase(std::remove_if(v.begin(), v.end(), [threshold](int x) {
    return x <= threshold;
}), v.end());

五、可变 lambda(mutable)

默认按值捕获的变量是只读的,想修改需加 mutable

int x = 0;
auto f = [x]() mutable { x++; std::cout << x; };
f();  // 输出 1(但不影响外部的 x)

六、返回类型推导 & 显式指定

auto f = [](int a, int b) -> double {
    return a / (double)b;
};

如果只有一条 return,可以省略 ->

auto f = [](int a, int b) { return a + b; };  // 推导为 int

在 C++ 中,Lambda 表达式是一种定义匿名函数对象的简洁方式,非常适合用于一次性使用的函数逻辑,尤其是在算法或回调中。


七、使用 std::function 存储 Lambda 表达式

#include <iostream>
#include <functional>
using namespace std;

int main() {
    function<int(int, int)> add = [](int a, int b) -> int {
        return a + b;
    };

    cout << "Sum of 3 and 4 is: " << add(3, 4) << endl; // 输出:7
    return 0;
}

八、Lambda 是函数对象(类)

auto f = [](int x) { return x * 2; };

struct LambdaEquivalent {
    int operator()(int x) const { return x * 2; }
};

所以可以存入 std::function

std::function<int(int)> func = [](int x) { return x * 2; };

九、Lambda 用于并发(线程/异步)

std::thread t([] {
    std::cout << "Hello from thread!" << std::endl;
});
t.join();

十、总结表格

特性 示例 说明
无捕获 [](){} 无依赖环境
按值捕获 [x](){} 捕获 x 的副本
按引用捕获 [&x](){} 修改外部变量
捕获所有 [=] / [&] 简洁,常用于泛用 lambda
mutable [x]() mutable { x++; } 允许修改副本
返回类型 -> T 用于多类型或精确控制

Java Lambda 表达式

在Java中,Lambda表达式是在Java 8引入的,它提供了一种更简洁的方式来表示匿名方法。Lambda表达式可以被用作函数式接口(只有一个抽象方法的接口)的实例。以下是Lambda表达式的基本语法和一些使用场景:

基本语法

(parameters) -> expression

或者

(parameters) -> { statements; }
  • parameters:参数列表,它可以为空,也可以包含一个或多个参数。
  • ->:Lambda操作符,读作"goes to"。
  • expression{ statements; }:你希望执行的代码体。如果只有一行语句,可以省略大括号和return关键字;如果有多条语句,则需要使用大括号,并且显式地写return语句(如果需要返回值的话)。

示例

  1. 无参数的Lambda表达式

假设有一个函数式接口Runnable,我们可以这样使用Lambda表达式:

Runnable runnable = () -> System.out.println("Hello World");
new Thread(runnable).start();
  1. 带有一个参数的Lambda表达式

对于Consumer<String>接口,你可以这样定义一个Lambda表达式:

Consumer<String> consumer = (str) -> System.out.println(str);
consumer.accept("Hello, Lambda!");
  1. 带有多个参数的Lambda表达式

比如,使用BiFunction<Integer, Integer, Integer>来计算两个数之和:

BiFunction<Integer, Integer, Integer> adder = (a, b) -> a + b;
System.out.println(adder.apply(5, 3)); // 输出8

使用场景

Lambda表达式非常适合用于集合的遍历、过滤和映射等操作,尤其是在与Stream API一起使用时。例如:

List<String> names = Arrays.asList("Alice", "Bob", "Charlie");
names.stream()
     .filter(name -> name.startsWith("A"))
     .forEach(System.out::println);

在这个例子中,我们首先创建了一个字符串列表,然后使用stream()方法将其转换为流。接着,我们使用filter方法和Lambda表达式来筛选出以"A"开头的名字,最后使用forEach方法打印每个名字。

Lambda表达式的引入极大地简化了Java代码的编写,特别是在处理集合数据时。同时,它们也使得代码更加易读和简洁。

Python中的lambda表达式

在 Python 中,lambda 表达式(也称为 匿名函数)是一种创建简单、一次性使用的函数的方式。它不像普通函数那样使用 def 关键字定义,而是使用 lambda 关键字,并且通常用于需要函数对象作为参数的场合,比如在 map()filter()sorted() 等函数中。


基本语法

lambda arguments: expression
  • arguments:可以是多个参数,用逗号分隔。
  • expression:是一个表达式,其结果就是这个 lambda 函数的返回值。

⚠️ 注意:lambda 函数没有 return 语句,它的返回值就是表达式的结果。


示例

1. 无参数的 lambda 表达式

greet = lambda: "Hello, world!"
print(greet())  # 输出:Hello, world!

2. 单个参数的 lambda 表达式

square = lambda x: x * x
print(square(5))  # 输出:25

3. 多个参数的 lambda 表达式

add = lambda a, b: a + b
print(add(3, 4))  # 输出:7

4. 在 map() 中使用 lambda

将列表中的每个元素平方:

numbers = [1, 2, 3, 4]
squared = list(map(lambda x: x ** 2, numbers))
print(squared)  # 输出:[1, 4, 9, 16]

5. 在 filter() 中使用 lambda

筛选出偶数:

numbers = [1, 2, 3, 4, 5, 6]
evens = list(filter(lambda x: x % 2 == 0, numbers))
print(evens)  # 输出:[2, 4, 6]

6. 在 sorted()sort() 中使用 lambda

按字符串长度排序:

words = ["banana", "apple", "cherry", "date"]
sorted_words = sorted(words, key=lambda word: len(word))
print(sorted_words)  # 输出:['date', 'apple', 'banana', 'cherry']

7. lambda 与条件表达式结合

max_val = lambda a, b: a if a > b else b
print(max_val(10, 20))  # 输出:20

lambda vs def 函数的区别

特性 lambda 表达式 普通函数 (def)
是否有名字 可以匿名 必须有名字
功能复杂度 简单的一行表达式 可以包含多条语句和逻辑
是否可复用 不适合重复使用 可复用
返回值 自动返回表达式结果 需要显式使用 return

使用场景建议

  • 临时使用一次的小函数
  • 作为参数传递给其他高阶函数(如 map、filter、sorted)
  • 提高代码简洁性和可读性(但不要过度使用导致难以理解)

注意事项

  • Lambda 表达式只能写一行表达式,不能包含复杂的语句或循环。
  • 虽然可以嵌套 lambda,但会降低可读性,不推荐。
posted @ 2025-07-02 17:47  aixueforever  阅读(16)  评论(0)    收藏  举报