我正在研究输入系统。在该系统中,对象可以在按下某个键时注册要调用的函数。但是,注册的方法是该对象的成员,因此我的注册函数必须如下所示:
void register(EventType类型,Class * object,void(Class :: * function)()){ //保存这个 }
问题是它不会总是注册一个函数的同一个类,所以这不起作用。无论如何围绕这个吗?
答案 0 :(得分:2)
您可以将std::function<void()>
存储在注册回调的类中,然后添加函数模板register
成员函数:
struct Foo
{
template <typename F>
void register(EventType type, F&& fun)
{
// make an std::function<void()> from fun and store
}
};
然后,您在调用者方面绑定Class
实例和Class
成员函数。
struct Bar { void bar() {} };
void foobar() { std::cout << "foobar!\n"; }
Foo f;
Bar b;
f.register(event1, std::bind(&Bar::bar, b)); // will call b.bar()
f.register(event2, foobar); // will call foobar()
答案 1 :(得分:0)
这是一种没有模板和函数指针的方法。你有一个观察者(回调)类,如下所示:
class MyCallback {
public:
virtual void run(int abc)
{
cout << "MyCallback::run(" << abc << ")" << endl;
}
};
然后使用父类MyCallback实例化您的观察者类:
class Test : public MyCallback
{
public:
void run(int abc)
{
MyCallback::run(abc);
}
};
调用所有观察者的类:
class Subject
{
vector<MyCallback*> observers;
public:
void reg_observer(MyCallback* cb)
{
observers.push_back(cb);
}
void call_out(int abc)
{
vector<MyCallback*>::iterator it;
for(it=observers.begin();it!=observers.end();it++)
{
(*it)->run(abc);
}
}
};
测试代码:
void testcb()
{
Test ttt;
Subject s;
s.reg_observer(&ttt);
s.call_out(123);
}