将一个类的方法指针存储到另一个类中

storing pointers of methods of one class into another class

本文关键字:存储 指针 另一个 方法 一个      更新时间:2023-10-16

我有类A,它有方法void fun(int, int)void fun1(int, int)。这些是非静态方法。

struct A {
void fun(int,int){}
void fun1(int,int){}
};

现在在类B中,我想存储指向其中一个方法的指针。

这意味着Bobject1将具有指向fun的指针,Bobject2将具有指向fun1的指针。

现在我的set_handler()和指向处理程序的指针必须是通用的。

一种方法是使用函数指针。 这样我就可以使用可以存储funfun1地址的void(A::*pointer)(int,int)

struct B {
typedef void(A::*pointer)(int,int);
pointer f;
void set_handler(pointer p) { f = p; }
};
int main() {
{
B object1;
object2.set_handler(&A::fun);
}
{
B object2;
object2.set_handler(&A::fun1);
}
}

我正在研究boost::bind()但它需要特定名称。如何在此处使用提升?

我把你的问题简化为运行实际使用指针执行某些操作的代码 - 所以我们知道目标何时实现:

住在科里鲁

#include <iostream>
struct A {
void fun(int  a, int b) { std::cout << __FUNCTION__ << "(" << a << "," << b << ")" << std::endl; }
void fun1(int a, int b) { std::cout << __FUNCTION__ << "(" << a << "," << b << ")" << std::endl; }
};
struct B {
typedef void (A::*pointer)(int, int);
pointer f;
void set_handler(pointer p) { f = p; }
void run(A& instance) {
(instance.*f)(42, 42);
}
};
int main() {
B object1;
B object2;
object1.set_handler(&A::fun);
object2.set_handler(&A::fun1);
A a;
object1.run(a);
object2.run(a);
}

指纹

fun(42,42)
fun1(42,42)

使用boost::functionstd::function

您必须允许实例参数(隐式this参数(:

住在科里鲁

struct B {
using function = std::function<void(A&, int, int)>;
function f;
void set_handler(function p) { f = p; }
void run(A& instance) {
f(instance, 42, 42);
}
};

打印相同的输出。当然,您可以使用相同的boost::functionboost::bind

绑定呢?

当您想要调整函数签名时,就会使用 Bind 。因此,例如,您希望绑定到任何A&实例,而无需实际将其传递给run()

住在科里鲁

#include <iostream>
#include <functional>
struct A {
std::string name;
void fun(int  a, int b) { std::cout << "name:" << name << " " << __FUNCTION__ << "(" << a << "," << b << ")" << std::endl; }
void fun1(int a, int b) { std::cout << "name:" << name << " " << __FUNCTION__ << "(" << a << "," << b << ")" << std::endl; }
};
struct B {
using function = std::function<void(int, int)>;
function f;
void set_handler(function p) { f = p; }
void run() {
f(42, 42);
}
};
int main() {
B object1;
B object2;
A a1 {"black"};
A a2 {"white"};
{
using namespace std::placeholders;
object1.set_handler(std::bind(&A::fun, &a1, _1, _2));
object2.set_handler(std::bind(&A::fun1, &a2, _1, _2));
}
object1.run();
object2.run();
}

哪些打印:

name:black fun(42,42)
name:white fun1(42,42)

更多善良

从 c++ 开始,你可以不用绑定及其讨厌的占位符(还有其他警告,比如按值存储所有参数的 bind (。相反,您可以使用 lambdas:

住在科里鲁

#include <iostream>
#include <functional>
struct A {
std::string name;
void fun(int  a, int b) { std::cout << "name:" << name << " " << __FUNCTION__ << "(" << a << "," << b << ")" << std::endl; }
void fun1(int a, int b) { std::cout << "name:" << name << " " << __FUNCTION__ << "(" << a << "," << b << ")" << std::endl; }
};
struct B {
using function = std::function<void(int, int)>;
function f;
void set_handler(function p) { f = p; }
void run() {
f(42, 42);
}
};
int main() {
B object1;
B object2;
object1.set_handler([](int a, int b) {
A local_instance {"local"};
local_instance.fun(a*2, b*3); // can even do extra logic here
});
A main_instance {"main"};
object2.set_handler([&main_instance](int a, int b) {
main_instance.fun1(a, b); // can even do extra logic here
});
object1.run();
object2.run();
}

指纹

name:local fun(84,126)
name:main fun1(42,42)