#include <iostream>
#include <deque>
struct Foo {
bool memberFunc() { std::cout << "memberFunc of Foo called." << std::endl; return true; }
};
struct Bar {
bool memberFunc() { std::cout << "memberFunc of Bar called." << std::endl; return true; }
};
struct func_base {
virtual ~func_base() {};
virtual bool operator()() const = 0;
};
template <typename C>
class func_wrapper : public func_base {
public:
typedef bool (C::*member_func_ptr_t)();
func_wrapper(member_func_ptr_t func_ptr, C* instance_ptr) : m_func_ptr(func_ptr), m_instance_ptr(instance_ptr) {}
bool operator()() const { return (m_instance_ptr->*m_func_ptr)(); }
private:
member_func_ptr_t m_func_ptr;
C* m_instance_ptr;
};
/* This function returns a pointer to dynamically *
* allocated memory and it is thus the callers *
* responsibility to deallocate the memory!! */
template <typename C>
func_base* make_wrapper(bool (C::*func_ptr)(), C* instance_ptr) {
return new func_wrapper<C>(func_ptr, instance_ptr);
}
int main() {
Foo foo;
Bar bar;
std::deque<func_base*> d;
d.push_back(make_wrapper(&Foo::memberFunc, &foo));
d.push_back(make_wrapper(&Bar::memberFunc, &bar));
for (std::deque<func_base*>::iterator it = d.begin(); it != d.end(); ++it) {
(**it)();
}
for (std::deque<func_base*>::iterator it = d.begin(); it != d.end(); ++it) {
delete *it;
}
}
I2luY2x1ZGUgPGlvc3RyZWFtPgojaW5jbHVkZSA8ZGVxdWU+CgpzdHJ1Y3QgRm9vIHsKICAgIGJvb2wgbWVtYmVyRnVuYygpIHsgc3RkOjpjb3V0IDw8ICJtZW1iZXJGdW5jIG9mIEZvbyBjYWxsZWQuIiA8PCBzdGQ6OmVuZGw7IHJldHVybiB0cnVlOyB9Cn07CgpzdHJ1Y3QgQmFyIHsKICAgIGJvb2wgbWVtYmVyRnVuYygpIHsgc3RkOjpjb3V0IDw8ICJtZW1iZXJGdW5jIG9mIEJhciBjYWxsZWQuIiA8PCBzdGQ6OmVuZGw7IHJldHVybiB0cnVlOyB9Cn07CgpzdHJ1Y3QgZnVuY19iYXNlIHsKICAgIHZpcnR1YWwgfmZ1bmNfYmFzZSgpIHt9OwogICAgdmlydHVhbCBib29sIG9wZXJhdG9yKCkoKSBjb25zdCA9IDA7Cn07Cgp0ZW1wbGF0ZSA8dHlwZW5hbWUgQz4KY2xhc3MgZnVuY193cmFwcGVyIDogcHVibGljIGZ1bmNfYmFzZSB7CnB1YmxpYzoKICAgIHR5cGVkZWYgYm9vbCAoQzo6Km1lbWJlcl9mdW5jX3B0cl90KSgpOwogICAgZnVuY193cmFwcGVyKG1lbWJlcl9mdW5jX3B0cl90IGZ1bmNfcHRyLCBDKiBpbnN0YW5jZV9wdHIpIDogbV9mdW5jX3B0cihmdW5jX3B0ciksIG1faW5zdGFuY2VfcHRyKGluc3RhbmNlX3B0cikge30KICAgIGJvb2wgb3BlcmF0b3IoKSgpIGNvbnN0IHsgcmV0dXJuIChtX2luc3RhbmNlX3B0ci0+Km1fZnVuY19wdHIpKCk7IH0KcHJpdmF0ZToKICAgIG1lbWJlcl9mdW5jX3B0cl90IG1fZnVuY19wdHI7CiAgICBDKiBtX2luc3RhbmNlX3B0cjsKfTsKCi8qIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhIHBvaW50ZXIgdG8gZHluYW1pY2FsbHkgKgogKiBhbGxvY2F0ZWQgbWVtb3J5IGFuZCBpdCBpcyB0aHVzIHRoZSBjYWxsZXJzICAgICoKICogcmVzcG9uc2liaWxpdHkgdG8gZGVhbGxvY2F0ZSB0aGUgbWVtb3J5ISEgICAgICAqLwp0ZW1wbGF0ZSA8dHlwZW5hbWUgQz4KZnVuY19iYXNlKiBtYWtlX3dyYXBwZXIoYm9vbCAoQzo6KmZ1bmNfcHRyKSgpLCBDKiBpbnN0YW5jZV9wdHIpIHsKICAgIHJldHVybiBuZXcgZnVuY193cmFwcGVyPEM+KGZ1bmNfcHRyLCBpbnN0YW5jZV9wdHIpOwp9CgppbnQgbWFpbigpIHsKICAgIEZvbyBmb287CiAgICBCYXIgYmFyOwoKICAgIHN0ZDo6ZGVxdWU8ZnVuY19iYXNlKj4gZDsKCiAgICBkLnB1c2hfYmFjayhtYWtlX3dyYXBwZXIoJkZvbzo6bWVtYmVyRnVuYywgJmZvbykpOwogICAgZC5wdXNoX2JhY2sobWFrZV93cmFwcGVyKCZCYXI6Om1lbWJlckZ1bmMsICZiYXIpKTsKCiAgICBmb3IgKHN0ZDo6ZGVxdWU8ZnVuY19iYXNlKj46Oml0ZXJhdG9yIGl0ID0gZC5iZWdpbigpOyBpdCAhPSBkLmVuZCgpOyArK2l0KSB7CiAgICAgICAgKCoqaXQpKCk7CiAgICB9CgogICAgZm9yIChzdGQ6OmRlcXVlPGZ1bmNfYmFzZSo+OjppdGVyYXRvciBpdCA9IGQuYmVnaW4oKTsgaXQgIT0gZC5lbmQoKTsgKytpdCkgewogICAgICAgIGRlbGV0ZSAqaXQ7CiAgICB9Cn0=