C++ Boost Lambda表达式详解
作者:无水先生
lambda表达式格式
lambda表达式的格式
[捕捉列表](参数列表)mutable->返回值类型{ 语句部分 };
其中参数列表、返回值类型是可选的,捕捉列表、函数体可以为空。
先来看一个较为简单的lamda表达式
int main(void) { auto add = [](int a, int b)->int {return a + b; }; cout << add(1, 2) << endl; return 0; }
mutable可以省略,暂时不考虑。
- 捕捉列表,捕捉列表的
[]
是千万不能省略的,编译器会根据[]
判断该表达式是否为lambda表达式,捕捉列表能够捕捉上下文的变量提供给lambda表达式使用。 - 参数列表,就和普通的函数传参是一样的,如果不需要参数,那么可以连同
()
一起省略 - mutable:默认情况下,lambda表达式参数列表和捕捉列表被修饰成const属性,而mutable的作用就是取消它的const属性。如果使用了mutable参数一定不能省略,如果参数为空,那么需要保留
()
。 - ->返回值类型。返回值类型明确或没有返回值的情况下,该部分可省略,编译器会对返回值类型进行推导。
- 语句部分。和不同函数的函数体内语句部分是一样的含义,函数体内不仅可以使用它的参数,还可以使用所有捕获到的变量。
所以最简单的lambda表达式应该是[]{}
lambda表达式又被称为匿名函数,无法被直接调用,它的底层其实也是仿函数类。需要借助auto将表达式赋值给一个变量。
说明Boost.Lambda
在 C++11 之前,您需要使用像 Boost.Lambda 这样的库来利用 lambda 函数。从 C++11 开始,这个库可以被视为已弃用,因为 lambda 函数现在是编程语言的一部分。如果您在不支持 C++11 的开发环境中工作,您应该在转向 Boost.Lambda 之前考虑 Boost.Phoenix。 Boost.Phoenix 是一个较新的库,如果您需要在没有 C++11 的情况下使用 lambda 函数,它可能是更好的选择。
lambda 函数的目的是使代码更紧凑且更易于理解(请参见示例 43.1)。
示例 43.1。带有 lambda 函数的 std::for_each()的
#include <boost/lambda/lambda.hpp> #include <boost/lambda/if.hpp> #include <vector> #include <algorithm> #include <iostream> int main() { std::vector<int> v{1, 3, 2}; std::for_each(v.begin(), v.end(), boost::lambda::if_then(boost::lambda::_1 > 1, std::cout << boost::lambda::_1 << "\n")); }
Boost.Lambda 提供了几个助手来创建无名函数。代码写在应该执行的地方,不需要包装在函数中,也不必显式调用函数。在示例 43.1 中,std::cout << boost::lambda::_1 << "\n" 是一个 lambda 函数,它需要一个参数,它在写入标准输出后跟一个新行。
boost::lambda::_1 是一个占位符,它创建一个需要一个参数的 lambda 函数。占位符中的数字决定了预期参数的数量,因此 boost::lambda::_2 预期两个参数,而 boost::lambda::_3 预期三个参数。 Boost.Lambda 只提供了这三个占位符。示例 43.1 中的 lambda 函数使用 boost::lambda::_1,因为 std::for_each() 需要一个一元函数。
包括 boost/lambda/lambda.hpp 以使用占位符。
请注意,\n 而不是 std::endl,在示例 43.1 中用于输出新行。如果您使用 std::endl,该示例将无法编译,因为 lambda 函数 std::cout << boost::lambda::_1 的类型与一元函数模板 std::endl() 预期的类型不同。因此,您不能使用 std::endl。
示例 43.2。带有 boost::lambda::if_then() 的 lambda 函数
#include <boost/lambda/lambda.hpp> #include <boost/lambda/if.hpp> #include <vector> #include <algorithm> #include <iostream> int main() { std::vector<int> v{1, 3, 2}; std::for_each(v.begin(), v.end(), boost::lambda::if_then(boost::lambda::_1 > 1, std::cout << boost::lambda::_1 << "\n")); }
头文件 boost/lambda/if.hpp 定义了可用于在 lambda 函数中创建 if 控制结构的结构。最简单的构造是函数模板 boost::lambda::if_then(),它需要两个参数:第一个参数是一个条件。如果条件为真,则执行第二个参数。两个参数都可以是 lambda 函数,如示例 43.2 所示。
除了 boost::lambda::if_then() 之外,Boost.Lambda 还提供函数模板 boost::lambda::if_then_else() 和 boost::lambda::if_then_else_return(),它们都需要三个参数。还为循环和转换运算符提供函数模板,并在 lambda 函数中抛出异常。 Boost.Lambda 定义的许多函数模板使得定义 lambda 函数成为可能,这些函数丝毫不逊色于普通的 C++ 函数。
到此这篇关于C++ Boost Lambda表达式详解的文章就介绍到这了,更多相关C++ Boost Lambda内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!