C++ 11 Lambda匿名函数学习

1 Lambada函数形式

[capture list] (params list) mutable exception-> return type { function body }

各项具体含义如下

  1. capture list:捕获外部变量列表
  2. params list:形参列表
  3. mutable指示符:用来说用是否可以修改捕获的变量
  4. exception:异常设定
  5. return type:返回类型
  6. function body:函数体

2 捕获外部参数的形式——引用形式和值形式

2.1 引用形式

应用形式可以修改捕获的外部变量。

#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main(int argc, char** argv)
{
	string s1("Hello World!");
	string s2("My God!!!!");

	auto func = [&s2](const string ss)  {
		cout<<"Get string:"<<ss<<endl; 
		s2[0] = '*';
		cout << s2 << endl;

	};

	func(s1);

}

输出:

Get string:Hello World!
*y God!!!!
[root@localhost c++11]# 

2.2 值形式

#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main(int argc, char** argv)
{
	string s1("Hello World!");
	string s2("My God!!!!");

	auto func = [s2](const string ss)  {
		cout<<"Get string:"<<ss<<endl; 
		s2[0] = '*';
		cout << s2 << endl;

	};

	func(s1);

}

编译不通过

lambda.cpp: In lambda function:
lambda.cpp:12:9: error: assignment of read-only location ‘s2.std::basic_string<_CharT, _Traits, _Alloc>::operator[]<char, std::char_traits<char>, std::allocator<char> >(0ul)’
   s2[0] = '*';
         ^
[root@localhost c++11]# 

如果我们添加mutable指示符,则可以编译通过。但是这里要注意的是,修改的是捕获变量的拷贝,而不是捕获变量本身。也就是值形式捕获,在lambada函数内部默认得到一个const类型的捕获变量的拷贝,如果添加mutable指示符,则得到一份非const的拷贝。

#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main(int argc, char** argv)
{
	string s1("Hello World!");
	string s2("My God!!!!");

	auto func = [s2](const string ss) mutable {
		cout<<"Get string:"<<ss<<endl; 
		s2[0] = '*';
		cout << s2 << endl;

	};

	func(s1);

	cout << s2 << endl;

}

输出:

Get string:Hello World!
*y God!!!!
My God!!!!
[root@localhost c++11]# 
可以看到并没有修改被捕获的变量本身。

2.3 隐式捕获

我们可以让编译判断我们要捕获那些变量,但是要指定是值捕获(使用=)还是引用捕获(使用&)

值捕获,没有改变变量:

#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main(int argc, char** argv)
{
	string s1("Hello World!");
	string s2("My God!!!!");

	auto func = [=](const string ss) mutable {
		cout<<"Get string:"<<ss<<endl; 
		s2[0] = '*';
		cout << s2 << endl;

	};

	func(s1);

	cout << s2 << endl;

}

输出:

Get string:Hello World!
*y God!!!!
My God!!!!
[root@localhost c++11]# 

引用捕获,改变变量本身

#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main(int argc, char** argv)
{
	string s1("Hello World!");
	string s2("My God!!!!");

	auto func = [&](const string ss) mutable {
		cout<<"Get string:"<<ss<<endl; 
		s2[0] = '*';
		cout << s2 << endl;

	};

	func(s1);

	cout << s2 << endl;

输出

*y God!!!!
*y God!!!!
[root@localhost c++11]# 

3 返回值类型

3.1 指定返回值类型

#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main(int argc, char** argv)
{
	string s1("Hello World!");
	string s2("My God!!!!");

	auto func = [&](const string ss) mutable -> int{

		return 1.1;

	};

	auto res = func(s1);

	cout << res << endl;

}

输出:

1
[root@localhost c++11]# 

3.2 省略返回值类型

1)如果function body中存在return语句,则该Lambda表达式的返回类型由return语句的返回类型确定; 

2)如果function body中没有return语句,则返回值为void类型。

#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main(int argc, char** argv)
{
	string s1("Hello World!");
	string s2("My God!!!!");

	auto func = [&](const string ss) mutable {

		return 1.1;

	};

	auto res = func(s1);

	cout << res << endl;

}

输出

1.1
[root@localhost c++11]# 




猜你喜欢

转载自blog.csdn.net/idwtwt/article/details/80634646