无法使用默认参数初始化 lambda 成员变量
Cannot initialize a lambda member variable with a default argument
我想用 c++17 编译下面的代码,这样我就可以传递任何具有特定签名的函数 (lambda),int(int)
,同时还允许默认参数:
template <class F = int(int)> // for deduction
struct A{
A(F f = [] (int x){return x;}) : f_{f} {}
F f_;
};
int main() {
A work([](int x){return x + 1;});
A not_work; // compile error.
}
但是,clang 发出错误:
a.cpp:6:4: error: data member instantiated with function type 'int (int)'
F f_;
^
a.cpp:11:4: note: in instantiation of template class 'A<int (int)>' requested here
A not_work;
^
我不明白为什么我传递lambda时可以初始化成员f_
而默认的lambda参数不能?
同时,有没有更好的方法来做到这一点?
如错误消息所述,您不能声明函数类型为 int(int)
的数据成员。
当将lambda传递给构造函数时,模板参数F
将被CTAD (since C++17)推导为lambda闭包类型;当什么都不传递时 F
将使用默认参数 int(int)
并且数据成员 f_
的类型也将是 int(int)
,这会导致错误。
您可以使用函数指针类型(lambdas 没有捕获可以隐式转换为函数指针)或 std::function<int(int)>
。例如
template <class F = int(*)(int)> // for deduction
struct A{
A(F f = [] (int x){return x;}) : f_{f} {}
F f_;
};
或
template <class F = std::function<int(int)>> // for deduction
struct A{
A(F f = [] (int x){return x;}) : f_{f} {}
F f_;
};
我想用 c++17 编译下面的代码,这样我就可以传递任何具有特定签名的函数 (lambda),int(int)
,同时还允许默认参数:
template <class F = int(int)> // for deduction
struct A{
A(F f = [] (int x){return x;}) : f_{f} {}
F f_;
};
int main() {
A work([](int x){return x + 1;});
A not_work; // compile error.
}
但是,clang 发出错误:
a.cpp:6:4: error: data member instantiated with function type 'int (int)'
F f_;
^
a.cpp:11:4: note: in instantiation of template class 'A<int (int)>' requested here
A not_work;
^
我不明白为什么我传递lambda时可以初始化成员f_
而默认的lambda参数不能?
同时,有没有更好的方法来做到这一点?
如错误消息所述,您不能声明函数类型为 int(int)
的数据成员。
当将lambda传递给构造函数时,模板参数F
将被CTAD (since C++17)推导为lambda闭包类型;当什么都不传递时 F
将使用默认参数 int(int)
并且数据成员 f_
的类型也将是 int(int)
,这会导致错误。
您可以使用函数指针类型(lambdas 没有捕获可以隐式转换为函数指针)或 std::function<int(int)>
。例如
template <class F = int(*)(int)> // for deduction
struct A{
A(F f = [] (int x){return x;}) : f_{f} {}
F f_;
};
或
template <class F = std::function<int(int)>> // for deduction
struct A{
A(F f = [] (int x){return x;}) : f_{f} {}
F f_;
};