C++中使用Lambda

本文讨论的是在C++ 11标准下使用Lambda表达式。


lambda表达式在python,C#等语言中运用都是十分广泛的。使用lambda表达式可以快速定义匿名的函数,方便使用且能防止非法调用。

lambda表达式在C++中的声明格式如下:

1. 传递方式可以为空,&,=,或者为每一个外部参数指明传递方式。= 表示为值传递方式,& 表示为引用传递方式。就算为空,中括号也不可以省略。

2. 参数列表即函数的参数,参数可以按值或者按引用传递。如果没有参数,可以省略(包括小括号)。

3. mutable是可选的,如果声明了mutable则可以修改按值传递进来的参数的拷贝(在lambda表达式外修改不可见)。

4. throw也是可选的,用来抛出函数处理过程中的异常,需制定抛出的异常的类型。

5. 返回类型是函数返回值的类型,在两种情况下可以省略,在后面叙述。

6. 函数体,实现功能的部分。


说了这么多,给一个实际的例子。将一个普通的函数转化为lambda表达式。

用函数声明写一个加法的实现:

int add(int x, int y)
{
	return x + y;
}

用lambda表达式改写

auto add = [](int x, int y) { return x + y; };

这两种声明方法的结果是相同的,调用都是采用一般的函数调用方式。给个调用的例子。

int res = add(1, 2);

由于写的lambda表达式本身就可以作为函数,所以可以把上面的lambda表达式的声明和调用写在一起。

int res = [](int x, int y) { return x + y; } (1, 2);


从上面的例子中可以发现,在lambda表达式中,并未指明返回类型。这就是我们所说的两种特殊情况之一,函数体内部只有一句return,可以自动根据表达式中参数类型确定返回类型。另一种特殊情况是无返回或返回void,可以不写。其他情况都要指明返回类型。

如果指明返回类型,上面的lambda表达式这样写:

[](int x, int y) -> int { return x + y; }


当然,lambda表达式肯定不只是这样用的。再给一个例子,让数组a的每一个元素+1。

用for循环做的代码就不给了。只讲用lambda怎么写。

如果这个问题给一个python程序员,肯定会很快写出:

map(lambda x: x + 1, a)

如果让一个C#程序员做,也可以很快写出来:

a = a.Select(x => x + 1);

如果让一个C++程序员做,用lambda表达式就是这么写:

std::for_each(a, a+10, [](int &i) {i += 1;});

上面列举了三种语言对于lambda表达式的使用。可能相对于其他编程语言,C++中的写法较繁琐一些。但lambda的引入也能使得代码更加简洁。


对于刚才中括号里面为什么必须要加&,再给一个例子。

[a, &b](int i) {b = a + i; }(5);
这个例子中,a和b并不在函数体中定义,而是一个外部的参数。对于外部参数,需要指明捕获方式是按值还是引用传递。这个例子中是对于a按值传递,因为b要修改必须按引用传递。在上一个例子中,只写一个&而并没有写明参数的名称,表示对所有参数都执行按引用传递。这一点和C#等编程语言是不同的,C#中只有按引用传递。


最后给大家看一行C++代码

[](){}();

各种括号,看似很奇怪,其实很合理,这就是lambda的使用。


——————————

在C++11中,参数列表中的类型必须是确定类型,即只允许下面的写法

auto add = [](int x, int y) { return x + y; };
在C++14中,允许泛型lambda,即可以使用下面的写法

auto add = [](auto x, auto y) { return x + y; };

文中所涉及的所有代码均在Visual Studio 2015中通过。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值