请考虑以下代码:
struct f{
void get(int a) {}
};
struct g1{
template <typename Arg>
void get(Arg a) {}
};
struct g2{
template <typename... Args>
void get(Args... args) {}
};
int f2()
{
std::bind(&f::get,f(),2); // (A)
std::bind(&g1::get<int>,g1(),2); // (B) redundant type specifier !
//std::bind(&g1::get,g1(),2); // compiler error !
std::bind(&g2::get<int, double>,g2(),2,1.1); // (C) redundant type specifiers !
//std::bind(&g2::get,g2(),2,1.1); // compiler error !
return 0;
}
在(B)和(C)的情况下是否可以摆脱冗余模板参数? 我希望std :: bind能自动从其参数中扣除类型。
我在考虑编写一个包含可变参数模板参数的包装器并使用 decltype可能隐藏这种冗余类型规范。
注意:我使用的是gcc 4.4
答案 0 :(得分:3)
我不认为这对于(成员)函数是可行的,因为g1::get
和g2::get
必须在可用之前用实际参数进行实例化。
使用函数对象,您可以编写一个带有模板模板参数的函数,以及可变参数;然后,此函数可以使用您提供的参数实例化函数对象模板,并在绑定参数之前默认构造实例:
template <
template <typename... Args> class VariadicFunc,
typename... ActualArgs >
auto mybind(ActualArgs... args)
-> decltype(std::bind(VariadicFunc<ActualArgs...>(), args...))
{
return std::bind(VariadicFunc<ActualArgs...>(), args...);
}
template <typename... Args>
struct functor
{
void operator()(Args... args) {}
};
int main()
{
mybind<functor>(1, 2); // instantiates a functor<int, int> and binds it
}
正如我之前所说的,这只能用于函数对象,而不能用于函数指针,因为你不能用模板函数指针来参数化模板。
答案 1 :(得分:1)
使用operator()
代替get
方法。它将以这种方式工作:
#include <functional>
#include <iostream>
struct g1{
typedef void result_type;
template <typename Arg>
result_type operator()(Arg a) {
std::cout << "g1()" << std::endl;
}
};
struct g2{
typedef void result_type;
template <typename... Args>
result_type operator()(Args... args) {
std::cout << "g2()" << std::endl;
}
};
int main()
{
std::bind(g1(),2)();
std::bind(g2(),2,1.1)();
return 0;
}
不幸的是,我找不到任何方法让它与成员函数一起使用。但是对于真正的函数对象,它可以工作。
还不幸的是,您需要声明result_type。