C++ 通过lambda函数转发附加参数
这是最小可复制代码C++ 通过lambda函数转发附加参数,c++,c++11,lambda,C++,C++11,Lambda,这是最小可复制代码 #include <iostream> #include <string> void bar(std::string s, int x){ std::cout <<std::endl<< __FUNCTION__<<":"<<s<<" "<<x; } using f_ptr = void(*)(std::strin
#include <iostream>
#include <string>
void bar(std::string s, int x){
std::cout <<std::endl<< __FUNCTION__<<":"<<s<<" "<<x;
}
using f_ptr = void(*)(std::string);
void foo(f_ptr ptr){
ptr("Hello world");
}
template<typename T> void fun(T f){
static int x;
std::cout <<std::endl<<x++<<std::endl;
f("Hello World");
}
int main()
{
//case:1
f_ptr ptr1 = [](std::string s){bar(s,10);};
// foo(ptr1);
//case:2
static int x =10;
f_ptr ptr2 = [x](std::string s){bar(s,x);};
//foo(ptr2);
//case:3
int y =10;
f_ptr ptr3 = [y](std::string s){bar(s,y);}; /* error*/
foo(ptr3);
//case:4
int z = 12;
fun([z](std::string s){bar(s,z);});
return 0;
}
我的问题是,
case:3
案例3
中,什么转换导致错误案例:4
中,类型名T
被推断为什么case:3
案例3
中,什么转换导致错误std::function
void foo(std::function<void(std::string)> f){
f("Hello world");
}
voidfoo(std::函数f){
f(“你好世界”);
}
或者像fun
那样直接使用lambda
案例:4
中,类型名T
被推断为什么该类型将是唯一的闭包类型;lambda表达式是该类型的prvalue表达式。一些详细信息,为什么会编译而案例3不会编译:
//case:2
static int x =10;
f_ptr ptr2 = [x](std::string s){bar(s,x);};
它可以编译,因为它实际上不捕获任何内容,因此lambda可以绑定到函数指针,这在有效捕获情况下是不允许的。标准上说:
5.1.1/2 lambda捕获中的名称应在lambda表达式的上下文范围内,且应为该名称或引用本地名称
具有自动存储持续时间的变量或引用
因此,静态变量捕获情况的行为至少没有指定,但不一定是未定义的行为(实现的自由度)
请注意,捕获静态变量可能会导致令人生疑的可怕问题,因为从捕获列表的语义中可能需要复制值,但实际上没有复制任何内容
还要注意的是,这个问题对于全局变量也是一样的(没有自动存储持续时间) 在案例2中,您没有捕获任何内容,因此
[x]
应该只是[]
(基本上与案例1相同),而在案例3中,lambda对象无法转换为指向普通函数的指针,因为它具有数据成员y
。在情况4中,T被推断为lambda的一种类型。
//case:2
static int x =10;
f_ptr ptr2 = [x](std::string s){bar(s,x);};