将成员函数作为多个类的参数
Posted
技术标签:
【中文标题】将成员函数作为多个类的参数【英文标题】:Take member functions as parameters from multiple classes 【发布时间】:2013-07-23 14:40:14 【问题描述】:我正在研究一个输入系统。在该系统中,对象可以注册一个函数,以便在按下某个键时调用。然而,注册的方法是该对象的成员,所以我的注册函数必须看起来像这样:
void register(EventType type, Class* object, void (Class::*function)()) //保存这个
问题是注册函数的类并不总是相同的,所以这行不通。反正有这个吗?
【问题讨论】:
模板。使用模板化的子类创建一个基本回调类。 【参考方案1】:您可以将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()
【讨论】:
调用这个函数会是什么样子?我认为 F&& 是一个函数指针。 @handuelF&&
是一种模板技术,它使用引用折叠来很好地处理左值或右值引用。你不必为此担心太多。我添加了一个小例子。我还在a blog 上写过类似的东西。
@handuel 请注意,这需要 C++11,但如果您没有编译器支持,那么您可以对 boost
执行几乎相同的操作(&&
除外) .
你知道这是否适用于 g++ 吗?当我调用编译器时,我是否必须使用命令行参数告诉它使用哪个标准?
@handuel 这取决于版本。我不确定所有功能需要什么版本才能工作,但我觉得 4.6 应该足够了。【参考方案2】:
这是一种不需要模板和函数指针的方法。你有一个像这样的观察者(回调)类:
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);
【讨论】:
以上是关于将成员函数作为多个类的参数的主要内容,如果未能解决你的问题,请参考以下文章