Как объекты Binder2nd, которые хранят указатели на функции-члены, могут использоваться на карте? - PullRequest
3 голосов
/ 22 марта 2011

Мой вопрос похож на этот . Мне нужно хранить указатели на функции-члены на карте. Функции-члены принимают аргумент, который должен быть связан определенным значением при построении карты. Как я могу это сделать? Должна ли карта иметь в качестве значения объект binder2nd.

Например:

enum { FOO, BAR };

exMap["foo"]  = bind2nd(&classA::Func, FOO);

Я не знаю, как объявить эту карту.

Ответы [ 3 ]

2 голосов
/ 22 марта 2011

Вот пример, который работает с использованием Boost.Function :

#include "boost/function.hpp"
#include <map>
#include <iostream>
#include <functional>

struct Foo {
    void bar(int x) {
        std::cout << "bar called with x=" << x << std::endl;
    }
};

int main()
{
    Foo foo;
    std::map<int, boost::function<void (Foo*)> > m;

    m[1] = std::bind2nd(std::mem_fun(&Foo::bar), 3);

    m[1](&foo);

    return 0;
}

Очевидно, что это невозможно с binder2nd, потому что это не конструируемый по умолчанию, который являетсятребование для значений std::map.

Поскольку вы не можете использовать Boost, вам придется написать свой собственный связыватель.

1 голос
/ 22 марта 2011

Вместо bind2nd вы можете сделать это вручную с помощью std::pair. Пример:

#include <map>
#include <functional>
#include <string>

enum { FOO, BAR };

class classA{
public:
    void Func(int){}
};

// define classAMemFn
typedef void (classA::*classAMemFn)(int);
// define element
typedef std::pair<classAMemFn, int> XElement;

typedef std::map<std::string, XElement> XMap;

void setup(XMap& xmap){
    xmap["FOO"]=std::make_pair(&classA::Func,FOO);
    xmap["BAR"]=std::make_pair(&classA::Func,BAR);
}

void Caller(XMap& xmap, const std::string& key, classA& obj){
    XMap::iterator it=xmap.find(key);
    if (it!=xmap.end()) {
        XElement e=it->second;
        (obj.*e.first)(e.second);
    }
}

Функция setup связывает указатели с функциями-членами и параметр с ключом строки.

Функция Caller заключает в себе грязную задачу поиска пары на карте и выполнения вызова.

0 голосов
/ 22 марта 2011

Как я понял из вашего комментария к вопросу, вам нужно преобразовать строку в enum, а затем вы хотите вызвать функцию со значением enum.
Если это так, почему вы все усложняете с помощью связывателей?

Вы можете просто сделать что-то вроде:

// Initialize your map with appropriate string -> enum mappings.

и

callYourFunction(yourMap[yourStringFromInput]);

Тип карты будет:

std::map<std::string, YourEnumType> yourMap;

И прототип функции:

SomeReturnType callYourFunction(YourEnumType e);

Вот и все, никаких переплетов;)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...