![](/img/trans.png)
[英]How to make function template, which takes std::vector and pointer to function?
[英]How to store pointer to function template which takes Callable object as one of its parameters
考虑以下示例:
template <typename T>
void f (T t) {
std::cout << t << std::endl;
}
template <typename T>
struct F {
static constexpr void (*m) (T) = &f;
};
和用法:
F<int>::m (10);
到现在为止还挺好。 当我想存储指向带有lambda表达式的函数模板的指针时,出现问题。 考虑一下这一点:
template <typename T, typename C>
void g (T t, C c) {
std::cout << c (t) << std::endl;
}
template <typename T, typename C>
struct G {
static constexpr void (*m) (T, C) = &g;
};
和用法:
auto l = [] (auto v) { return v; };
G<int, decltype (l)>::m (20, l);
在GCC 5.3.1上使用以下命令进行编译时:
g++-5 -std=c++14 -Wall -Wextra -Wpedantic -Werror=return-type main.cpp -o main
我有:
‘constexpr void (* const G<int, main(int, char**)::<lambda(auto:1)> >::m)(int, main(int, char**)::<lambda(auto:1)>)’, declared using local type ‘main(int, char**)::<lambda(auto:1)>’, is used but never defined [-fpermissive]
为什么会这样?
有什么办法可以使此代码起作用?
我不感兴趣的一种可能的解决方案:
struct O {
template <typename T>
T operator() (T v) {
return v;
}
};
用法:
G<int, O>::m (20, O {});
如果删除某些内容,该错误将显示:
[...]
m
[...]已使用但从未定义[-fpermissive]
因此,只需遵循编译器的命令并对其进行定义:
template <class T, class C>
constexpr void (*G<T,C>::m)(T,C);
现在就可以了。 这是因为在C ++ 14中,您需要从[class.static.data]添加静态constexpr数据成员的定义:
如果[静态数据]成员在程序中被奇数次使用([basic.def.odr]),并且仍应在命名空间范围内定义,并且命名空间范围定义不应包含初始化程序。
由于p0386 ,对于constexpr
静态数据成员,在C ++ 17中不再需要此方法。 文本现在显示为 :
如果[constant data]成员是用
constexpr
说明符声明的,则可以在没有初始化程序的命名空间范围内重新声明它(不建议使用此用法;请参见[depr.static_constexpr])。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.