2013-04-25 219 views
2

我有一个类:转换类型为int(C :: *)(INT,CHAR)为int类型(INT,CHAR)

struct C { 
    int F(int, char) { return 0; } 
}; 

,我需要创建一个std::function,它会调用C::F一个变量c功能:

C c; 
std::function<int(int, char)> f; 
... 
f = std::bind(&C::F, &c, _1, _2); 

但如果函数的签名被改变,我需要改变的std ::功能以及。

,所以我想不重复签名:

C c; 
std::function<delete_class<decltype(&C::F)>::type> f; 
... 
f = std::bind(&C::F, &c, _1, _2); 

其中delete_class是一些神奇的帮手,它改变输入int(C::*)(int, char)int(int, char)

我怀疑,我可以在boost::mplboost::function_types的帮助下实现它,但我做不到。

有人,谁有经验,告诉我该怎么做?

PS。 VS 2010

+0

你能不能只需使用'auto f = std :: bind(&C :: F,&c,_1,_2);'? – soon 2013-04-25 16:44:34

+0

在真正的应用f是一个结构的成员,所以我不能使用“自动”那里 – Alek86 2013-04-25 16:51:13

回答

4

如果你需要一个类型特征delete_class你的愿望的作品,这其中应该做的工作:

template<typename S> 
struct delete_class; 

template<typename R, typename C, typename... Ts> 
struct delete_class<R (C::*)(Ts...)> 
{ 
    using type = R(Ts...); 
}; 

下断言将被满足:

static_assert(
    std::is_same<delete_class<decltype(&C::F)>::type, 
    int(int, char) 
    >::value, "!"); 

你然后可以使用delete_class<>您建议的方式:

std::function<delete_class<decltype(&C::F)>::type> f; 
C c; 
f = std::bind(&C::F, &c, _1, _2); 

这是一个live example

编辑:

如果仅限于VC10支持(即无可变参数模板),你必须定义delete_class主模板的几个部分特例:

template<typename S> 
struct delete_class; 

template<typename R, typename C> 
struct delete_class<R (C::*)()> 
{ 
    typedef R(type)(); 
}; 

template<typename R, typename T> 
struct delete_class<R (C::*)(T)> 
{ 
    typedef R(type)(T); 
}; 

template<typename R, typename T, typename U> 
struct delete_class<R (C::*)(T, U)> 
{ 
    typedef R(type)(T, U); 
}; 

template<typename R, typename T, typename U, typename V> 
struct delete_class<R (C::*)(T, U, V)> 
{ 
    typedef R(type)(T, U, V); 
}; 

// And so on... 
+0

哦,对不起,忘了提及:VS2010 ... – Alek86 2013-04-25 16:46:28

+0

@ Alek86:上面应该与VC10 – 2013-04-25 16:47:41

+0

VS 2010不支持variadic模板:( – Alek86 2013-04-25 16:50:09