我有一些功能模板,例如
template <typename T>
void foo(T);
template <typename T>
void bar(T);
// others
我需要将每个算法传递给一个算法,该算法会用各种类型调用它,例如
template <typename F>
void some_algorithm(F f)
{
// call f with argument of type int
// call f with argument of type SomeClass
// etc.
}
我无法传递未实例化的函数模板,但我无法使用任何特定类型对其进行实例化,因为some_algorithm
需要使用多种不同类型的参数调用它。
我可以将我的函数模板调整为多态函数对象,例如
struct foo_polymorphic
{
template <typename T>
void operator()(T t)
{
foo(t);
}
};
然后将其作为some_algorithm(foo_polymorphic())
传递。但这需要为我的每个功能模板编写一个单独的适配器。
是否有泛型方式将函数模板调整为多态函数对象,即我可以为我需要调整的每个函数模板重用的一些机制,而不必为每一个单独声明一些东西?
答案 0 :(得分:2)
问题的简短版本被赋予重载名称f
,如何简洁地编写对象ff
,以便ff(a0, a1, a2, ...)
最终调用f(a0, a1, a2, ...)
。
多态仿函数,你如何指出自己,是通常的解决方案。但它必须在线外定义(因为它有一个模板成员),所以我会考虑到我的答案不够简洁。
目前lambda表达式产生一个单态仿函数,因此它们很接近但不完全存在。
// set of functions overloaded on int and double
void f(int);
void f(double);
auto ff = [](int i) { return f(i); };
正如GMan在评论中所指出的那样,多态lambda会(应该?)是简明地编写内联多态函子的解决方案。
与此同时,可以编写一个make_overload
帮助器,将多个仿函数合并为一个,这样
auto ff = make_overload(
[](int arg0) { return f(arg0); }
, [](double arg0) { return f(arg0); } );
将“捕获”整个重载集。也许Boost.Preprocessor宏可以在这里提供帮助,以便auto ff = POLYMORPHIC_LAMBDA( 1, (int)(double), { return f(arg0); } );
可以内联使用。我怀疑存在arity限制(因此第一个宏参数),与通常的外部手写多态仿函数解决方案不同;所以这对例如可变函数模板。
答案 1 :(得分:1)
为什么不能使用模板模板参数?你说你不能通过你的模板未经实例化,但我不确定你以前是否听说过这个,告诉我你是否有这个并且它不起作用。
我不知道你的代码结构是什么样的,但是你可以做点什么
我知道这有效,但不知道这是不是你想要的:
template<typename T>
T some_algorithm(T data) { return T(); } // just returning nothing for example
template<typename T, T(*Something)(T)>
class FuncClass {
public:
T run(T data) { return Something(data); }
};
template<typename T, typename Functor>
void apply_algorithm(T data) {
Functor F;
F.run(data);
}
int main() {
int mydata = 4;
apply_algorithm<int, FuncClass<int, some_algorithm<int> > >(mydata);
cin.get();
}