怕相思,已相思,轮到相思没处辞,眉间露一丝。—— 长相思·|

xiaoluosibky

园龄:1年3个月粉丝:11关注:5

C++ Lambda表达式笔记

1. 什么是 Lambda 表达式?

Lambda 表达式是 C++11 引入的一种特性,允许定义匿名函数(没有名字的函数),并且可以像普通函数一样调用,甚至可以作为参数传递给其他函数。

基本语法:

[capture_list](parameters) -> return_type { function_body };
  • [capture_list]:捕获列表,决定外部变量如何被 lambda 捕获。
  • (parameters):参数列表,与普通函数的参数类似。
  • -> return_type(可选):返回类型,通常可以省略,由编译器自动推断。
  • { function_body }:函数体,包含要执行的具体逻辑。

2. Lambda 表达式的基本用法

  • 无参数、无返回值

    []() { std::cout << "Hello, Lambda!" << std::endl; }();

    输出:

    Hello, Lambda!
  • 有参数、返回值

    auto add = [](int a, int b) { return a + b; };
    std::cout << add(2, 3) << std::endl; // 输出 5
  • 显式指定返回类型

    auto divide = [](int a, int b) -> double {
    return static_cast<double>(a) / b;
    };
    std::cout << divide(5, 2) << std::endl; // 输出 2.5

3. 捕获列表([capture_list]

捕获列表决定 lambda 如何访问外部作用域中的变量。可以按值捕获或按引用捕获。

(1) 空捕获列表:[]
  • 不捕获任何外部变量。
  • 仅适用于 lambda 完全独立的情况。

示例:

auto print = []() { std::cout << "Independent Lambda" << std::endl; };
print();
(2) 按值捕获:[x]
  • 捕获外部变量 x 的副本,lambda 内的修改不会影响原变量。

示例:

int x = 5;
auto lambda = [x]() { std::cout << x << std::endl; };
lambda(); // 输出 5
x = 10; // 修改原变量
lambda(); // 仍输出 5
(3) 按引用捕获:[&x]
  • 捕获外部变量 x 的引用,lambda 内的修改会影响原变量。

示例:

int x = 5;
auto lambda = [&x]() { x += 10; };
lambda();
std::cout << x << std::endl; // 输出 15
(4) 捕获所有外部变量:[=][&]
  • [=]:按值捕获所有外部变量。
  • [&]:按引用捕获所有外部变量。

示例:

int x = 5, y = 10;
auto lambda1 = [=]() { std::cout << x + y << std::endl; }; // 按值捕获
auto lambda2 = [&]() { x += y; }; // 按引用捕获
lambda1(); // 输出 15
lambda2();
std::cout << x << std::endl; // 输出 15
(5) 混合捕获:[=, &x][&, x]
  • [=, &x]:按值捕获所有变量,但对 x 按引用捕获。
  • [&, x]:按引用捕获所有变量,但对 x 按值捕获。

示例:

int x = 5, y = 10;
auto lambda = [=, &y]() { y += x; }; // x 按值,y 按引用
lambda();
std::cout << y << std::endl; // 输出 15

4. 使用 Lambda 表达式排序

Lambda 表达式经常用于自定义排序规则,例如在 std::sort 中。

  • 升序排序

    std::vector<int> vec = {5, 2, 9, 1};
    std::sort(vec.begin(), vec.end(), [](int a, int b) { return a < b; });
    // vec: {1, 2, 5, 9}
  • 降序排序

    std::sort(vec.begin(), vec.end(), [](int a, int b) { return a > b; });
    // vec: {9, 5, 2, 1}
  • 复杂排序规则

    std::sort(vec.begin(), vec.end(), [](int a, int b) {
    if (a % 2 == b % 2) return a > b; // 同为奇数或偶数,按降序
    return a % 2 < b % 2; // 偶数优先
    });
    // 假设 vec = {5, 2, 4, 7, 8}
    // 排序后:{8, 4, 2, 7, 5}

5. Lambda 表达式的实际应用场景

  1. 代替普通函数:用于实现一次性的功能,减少定义单独函数的冗余。
  2. 自定义排序:灵活定义排序规则(如 std::sort)。
  3. 回调函数:用于事件响应或异步处理(如 std::for_each)。
  4. 函数式编程:与标准库的函数式接口(如 std::transform)结合使用。
  5. 捕获变量用于计算:简化闭包的实现。

6. 示例:捕获外部变量的高级应用

int base = 10;
auto multiplier = [base](int x) { return base * x; };
std::cout << multiplier(2) << std::endl; // 输出 20
  • 捕获 base,并使用其值进行计算。
  • 这使得 lambda 可以与外部变量结合实现更多功能。

7. 总结

Lambda 表达式的优势:

  1. 简洁:减少了定义额外函数的冗余代码。
  2. 灵活:可以捕获外部变量,轻松实现闭包。
  3. 高效:与标准库算法结合(如 std::sortstd::transform),使代码更清晰。

常用模式:

  • 无捕获[]() {}
  • 按值捕获[x]() {}[=]() {}
  • 按引用捕获[&x]() {}[&]() {}
  • 混合捕获[=, &x][&, x]

Lambda 表达式是现代 C++ 编程的重要工具,值得熟练掌握!

本文作者:xiaoluosibky

本文链接:https://www.cnblogs.com/lyx9785/p/18555520

版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。

posted @   xiaoluosibky  阅读(21)  评论(0编辑  收藏  举报
点击右上角即可分享
微信分享提示
评论
收藏
关注
推荐
深色
回顶
收起