C++ lambda 底层实现

1. Lambda表达式

capture-list:捕获列表,用于指定在lambda函数体中可访问的外部变量。
parameter-list:参数列表,类似于普通函数声明中的参数列表。
return-type:返回类型,指定lambda表达式返回值类型。
{ body }:函数体,实现lambda表达式要执行的操作。

2. Lambda底层实现

Lambda表达式主要是通过匿名类,重载operator() 运算符,至于捕获变量,无论是按值还是按引用捕获,都是作为类对象的成员变量。

在调用lambda表达式处,构造类对象,通过调用operator()操作符来达到函数调用的效果。

2.1 当捕获列表为空时

#include <iostream>

void test() {
	auto add = [](int a, int b) { return a + b; };
	int ret = add(10, 20);
	std::cout << ret << std::endl;
}

int main() {
	test();
	return 0;
}

对应的C++底层实现: 参考网址C++ Insights

void test()
{
    
  class __lambda_4_13  // 定义一个匿名类, 
  {
    public: 
    inline  int operator()(int a, int b) const // 重载operator() 操作符
    {
      return a + b;
    }
    
    using retType_4_13 = int (*)(int, int);
    inline constexpr operator retType_4_13 () const noexcept
    {
      return __invoke;
    };
    
    private: 
    static inline /*constexpr */ int __invoke(int a, int b)
    {
      return __lambda_4_13{}.operator()(a, b);
    }
    
    
    public:
    // /*constexpr */ __lambda_4_13() = default;
    
  };
  
  __lambda_4_13 add = __lambda_4_13{};  //定义一个类对象

  int ret = add.operator()(10, 20);     //调用operator() 操作符

  std::cout.operator<<(ret).operator<<(std::endl);
}

2.2 当捕获列表非空时,

#include <iostream>

void test() {
	int sum = 0; 
	int value1 = 100;
	
	auto add = [&sum, value1](int num1, int num2) { return sum = num1 + num2 + value1;};

	int ret = add(10, 20);
	std::cout << sum << std::endl;
}

int main() {
	test();
	return 0;
}

对应的C++底层实现,  参考网址C++ Insights

void test()
{
  int sum = 0;
  int value1 = 100;
    
  class __lambda_7_13
  {
    public: 
    inline  int operator()(int num1, int num2) const  //重载operator() 运算符
    {
      return sum = ((num1 + num2) + value1);  //此处修改sum的值
    }
    
    private: 
    int & sum;     // 按照引用传递,
    int value1;    // 按照值传递
    
    public:
    __lambda_7_13(int & _sum, int & _value1)  // 匿名类构造函数
    : sum{_sum}
    , value1{_value1}
    {}
    
  };
  
  __lambda_7_13 add = __lambda_7_13{sum, value1}; //定义一个匿名变量

  int ret = add.operator()(10, 20);   //调用 operator()函数

  std::cout.operator<<(sum).operator<<(std::endl);
}

2.3 C++14 允许 Lambda 表达式参数使用 auto 关键字,这样 Lambda 表达式就可以更加灵活地处理不同类型的参数,从而增强了其泛型编程的能力:

例如 : auto lambda = [](auto x, auto y) { return x + y; }; 

#include <iostream>

void test() {
	int sum = 0;
	int value1 = 100;

	auto add = [&sum, value1](auto num1, auto num2) { return sum = num1 + num2 + value1;};

	auto ret = add(10, 20);
	std::cout << sum << std::endl;
}

int main() {
	test();
	return 0;
}

 对应的C++底层实现,  参考网址C++ Insights

void test()
{
  int sum = 0;
  int value1 = 100;
    
  class __lambda_7_13   //匿名类
  {
    public: 
    template<class type_parameter_0_0, class type_parameter_0_1>
    inline  auto operator()(type_parameter_0_0 num1, type_parameter_0_1 num2) const //模板函数 operator()
    {
      return sum = ((num1 + num2) + value1);
    }
    
    #ifdef INSIGHTS_USE_TEMPLATE
    template<>
    inline /*constexpr */ int operator()<int, int>(int num1, int num2) const
    {
      return sum = ((num1 + num2) + value1);
    }
    #endif
    
    private: 
    int & sum;    //按引用传递
    int value1;   //按值传递
    
    public:
    __lambda_7_13(int & _sum, int & _value1)  //定义类的构造函数
    : sum{_sum}
    , value1{_value1}
    {}
    
  };
  
  __lambda_7_13 add = __lambda_7_13{sum, value1};  //定义一个匿名类对象

  int ret = add.operator()(10, 20);  //调用 operator()函数

  std::cout.operator<<(sum).operator<<(std::endl);
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值