通用成员函数指针
Generic member function pointer
我想知道在标准 C++ 中是否有一种方法(看起来这不受支持,但也许我没仔细看)声明指向任何 class' 具有相同签名的成员函数的指针.例如,X 和 Y 具有具有相同签名的 echoX 和 echoY 方法
class X{
int val;
public:
int echoX(int v) {
val = v;
return v; }
int getValue() const { return val; }
};
class Y{
int val;
public:
int echoY(int v) {
val = v;
return v;
}
int getValue() const { return val; }
};
一些 C++ 实现通过扩展允许此功能(例如 VCL 使用 __closure
关键字)。
typedef int (__closure *IntFunPtr)(int);
现在,编写一个能够调用 X::echoX
或 Y::echoY
的函数是微不足道的
void CallObjectMethod(IntFunPtr fPtr, int val){
fPtr(val);//this can call any member method that accepts an int and returns an int
}
X x, x1;
CallObjectMethod(&x.echoX,4);
CallObjectMethod(&x1.echoX,20);
Y y, y1;
CallObjectMethod(&y.echoY,10);
CallObjectMethod(&y1.echoY,15);
此功能对于实现事件处理程序等非常有用。
谢谢
"For example, X and Y have echoX and echoY methods with the same signature"
Afaik 它们没有相同的签名,它们对 class 实例有一个隐式的第一个参数。通常你会选择 std::function
来去掉第一个参数。
#include <functional>
class X { public: int echoX(int v) {return v; } };
class Y { public: int echoY(int v) {return v; } };
typedef std::function<int(int)> IntFunction;
int echo(IntFunction func, int v)
{
return func(v);
}
int main()
{
int v = 5;
X x;
Y y;
int a = echo(std::bind(&X::echoX, x, std::placeholders::_1), v);
int b = echo(std::bind(&Y::echoY, y, std::placeholders::_1), v);
}
您可以创建一个通用模板函数,它接受您感兴趣的签名,传入对象的实例和指向成员函数的指针。例如:
template<typename T>
void CallObjectMethod(int(T::*func)(int), T& obj, int val)
{
cout << (obj.*func)(val);
}
现在像您在示例中提到的那样调用它:
X x, x1;
CallObjectMethod(&X::echoX, x, 10);
CallObjectMethod(&X::echoX, x1, 20);
对于对象 Y,您可以执行如下操作:
Y y, y1;
CallObjectMethod(&Y::echoY, y, 10);
CallObjectMethod(&Y::echoY, y1, 20);
我想知道在标准 C++ 中是否有一种方法(看起来这不受支持,但也许我没仔细看)声明指向任何 class' 具有相同签名的成员函数的指针.例如,X 和 Y 具有具有相同签名的 echoX 和 echoY 方法
class X{
int val;
public:
int echoX(int v) {
val = v;
return v; }
int getValue() const { return val; }
};
class Y{
int val;
public:
int echoY(int v) {
val = v;
return v;
}
int getValue() const { return val; }
};
一些 C++ 实现通过扩展允许此功能(例如 VCL 使用 __closure
关键字)。
typedef int (__closure *IntFunPtr)(int);
现在,编写一个能够调用 X::echoX
或 Y::echoY
void CallObjectMethod(IntFunPtr fPtr, int val){
fPtr(val);//this can call any member method that accepts an int and returns an int
}
X x, x1;
CallObjectMethod(&x.echoX,4);
CallObjectMethod(&x1.echoX,20);
Y y, y1;
CallObjectMethod(&y.echoY,10);
CallObjectMethod(&y1.echoY,15);
此功能对于实现事件处理程序等非常有用。
谢谢
"For example, X and Y have echoX and echoY methods with the same signature"
Afaik 它们没有相同的签名,它们对 class 实例有一个隐式的第一个参数。通常你会选择 std::function
来去掉第一个参数。
#include <functional>
class X { public: int echoX(int v) {return v; } };
class Y { public: int echoY(int v) {return v; } };
typedef std::function<int(int)> IntFunction;
int echo(IntFunction func, int v)
{
return func(v);
}
int main()
{
int v = 5;
X x;
Y y;
int a = echo(std::bind(&X::echoX, x, std::placeholders::_1), v);
int b = echo(std::bind(&Y::echoY, y, std::placeholders::_1), v);
}
您可以创建一个通用模板函数,它接受您感兴趣的签名,传入对象的实例和指向成员函数的指针。例如:
template<typename T>
void CallObjectMethod(int(T::*func)(int), T& obj, int val)
{
cout << (obj.*func)(val);
}
现在像您在示例中提到的那样调用它:
X x, x1;
CallObjectMethod(&X::echoX, x, 10);
CallObjectMethod(&X::echoX, x1, 20);
对于对象 Y,您可以执行如下操作:
Y y, y1;
CallObjectMethod(&Y::echoY, y, 10);
CallObjectMethod(&Y::echoY, y1, 20);