Am I reinventing the wheel with this trivial method call forwarding class?

心已入冬 提交于 2019-12-06 03:53:57

问题


I just found myself creating a class

template <typename T> struct invoker {
  void operator()(T& it) const {it();}
};

so I could pass an invoker<foo> to something (which isn't under my control) which wants to call invoker<foo>::operator()(foo&) on it repeatedly with different foo instances, to get it to forward those calls to the foo's foo::operator()() method.

I know it's only a few lines, but this seems like the sort of thing which is probably already provided for by STL's functional, or boost::bind somehow. Except I can't see the trick, if there is one. (I'm sure I'm not the first person to use something very like this; does it have a name ?)


回答1:


Yeah, you're reinventing the wheel. std::mem_fun_ref does what you want.

std::vector<foo> foos;

...

std::for_each(foos.begin(), foos.end(), std::mem_fun_ref(&foo::operator()));

Alternatively:

std::vector<foo*> foos;

...

std::for_each(foos.begin(), foos.end(), std::mem_fun(&foo::operator()));

Not having to mess with whether your param is ptr or not is one great benefit of boost::mem_fn.

Anything much more complex than that though and you begin running into trouble with the C++03 binders and need something more expressive like boost.bind.




回答2:


Well, you can use std::bind, probably boost::bind as well to achieve the same behaviour:

#include <string>
#include <iostream>
#include <functional>

struct foo {
    void operator()() {
        std::cout << "Hallo, im at addr: " << std::hex << this << std::endl;
    }
};

int main() {
    std::function<void(foo*)> fun = std::bind(&foo::operator(), std::placeholders::_1);
    foo f1, f2;
    fun(&f1);
    fun(&f2);
}

Outputs:

Hallo, im at addr: 0xbffc396a
Hallo, im at addr: 0xbffc3969

If you use a template class for the argument type, you can have the same behvaiour without reinventing the wheel.

Edit: as Crazy Eddie pointed out, you can just use boost::mem_fn or std::mem_fn:

std::function<void(foo*)> fun = std::mem_fn(&foo::operator());

Instead of bind.



来源:https://stackoverflow.com/questions/10610307/am-i-reinventing-the-wheel-with-this-trivial-method-call-forwarding-class

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!