将指向成员函数的指针转换为 std::function
Converting pointer to member function to std::function
我有一个稍微复杂的用例,将成员函数指针传递给外部函数,然后由成员函数再次调用(别问!)。我正在学习 std::function
和 std::mem_fn
,但我似乎无法转换我的旧学校函数指针
void (T::*func)(int)
到 std::function<void (T::*)(int) func>
在下面的代码中,我希望能够在 anotherMember
的调用中将 std::function 传递给 memFuncTaker
#include "class2.hpp"
#include <iostream>
class outer{
public:
void aMember(int a){
std::cout << a <<std::endl;
}
void anotherMember(double){
memFuncTaker(this, &outer::aMember);
}
};
template<class T>
void memFuncTaker(T* obj , void (T::*func)(int) ){
(obj->*func)(7);
}
当您将 std::function
绑定到非静态成员函数指针时,它 "reveals" 隐藏 this
参数,使其成为结果仿函数的第一个显式参数。因此,在 outer::aMember
的情况下,您将使用 std::function<void(outer *, int)>
并最终得到一个双参数仿函数
#include <functional>
#include <iostream>
template<class T>
void memFuncTaker(T *obj , std::function<void(T *, int)> func){
func(obj, 7);
}
class outer{
public:
void aMember(int a){
std::cout << a <<std::endl;
}
void anotherMember(double){
memFuncTaker(this, std::function<void(outer *, int)>{&outer::aMember});
}
};
int main() {
outer o;
o.anotherMember(0);
}
http://coliru.stacked-crooked.com/a/5e9d2486c4c45138
当然,如果您愿意,可以绑定该仿函数的第一个参数(通过使用 std::bind
或 lambda),因此再次 "hide" 它
#include <functional>
#include <iostream>
using namespace std::placeholders;
void memFuncTaker(std::function<void(int)> func){
func(7);
}
class outer{
public:
void aMember(int a){
std::cout << a <<std::endl;
}
void anotherMember(double){
memFuncTaker(std::function<void(int)>(std::bind(&outer::aMember, this, _1)));
}
};
int main() {
outer o;
o.anotherMember(0);
}
请注意,在此版本中 memFuncTaker
不再必须是模板(这恰好是 std::function
的主要目的之一 - 使用类型擦除技术 "de-templatize"代码)。
我有一个稍微复杂的用例,将成员函数指针传递给外部函数,然后由成员函数再次调用(别问!)。我正在学习 std::function
和 std::mem_fn
,但我似乎无法转换我的旧学校函数指针
void (T::*func)(int)
到 std::function<void (T::*)(int) func>
在下面的代码中,我希望能够在 anotherMember
memFuncTaker
#include "class2.hpp"
#include <iostream>
class outer{
public:
void aMember(int a){
std::cout << a <<std::endl;
}
void anotherMember(double){
memFuncTaker(this, &outer::aMember);
}
};
template<class T>
void memFuncTaker(T* obj , void (T::*func)(int) ){
(obj->*func)(7);
}
当您将 std::function
绑定到非静态成员函数指针时,它 "reveals" 隐藏 this
参数,使其成为结果仿函数的第一个显式参数。因此,在 outer::aMember
的情况下,您将使用 std::function<void(outer *, int)>
并最终得到一个双参数仿函数
#include <functional>
#include <iostream>
template<class T>
void memFuncTaker(T *obj , std::function<void(T *, int)> func){
func(obj, 7);
}
class outer{
public:
void aMember(int a){
std::cout << a <<std::endl;
}
void anotherMember(double){
memFuncTaker(this, std::function<void(outer *, int)>{&outer::aMember});
}
};
int main() {
outer o;
o.anotherMember(0);
}
http://coliru.stacked-crooked.com/a/5e9d2486c4c45138
当然,如果您愿意,可以绑定该仿函数的第一个参数(通过使用 std::bind
或 lambda),因此再次 "hide" 它
#include <functional>
#include <iostream>
using namespace std::placeholders;
void memFuncTaker(std::function<void(int)> func){
func(7);
}
class outer{
public:
void aMember(int a){
std::cout << a <<std::endl;
}
void anotherMember(double){
memFuncTaker(std::function<void(int)>(std::bind(&outer::aMember, this, _1)));
}
};
int main() {
outer o;
o.anotherMember(0);
}
请注意,在此版本中 memFuncTaker
不再必须是模板(这恰好是 std::function
的主要目的之一 - 使用类型擦除技术 "de-templatize"代码)。