2012-10-05 2 views
1

J'essaie de créer une fonction boost :: qui permet de définir une variable membre d'un objet. J'ai créé l'exemple le plus simple auquel je puisse penser pour comprendre ce que j'essaie (et j'échoue) de faire. J'ai l'impression d'avoir une idée de boost :: bind, mais je suis nouveau pour booster et je crois que j'utilise incorrectement la fonction boost ::.Utiliser boost :: function et boost :: bind vers une variable membre

#include <iostream> 
#include <Boost/bind.hpp> 
#include <boost/function.hpp> 

class Foo 
{ 
public: 
    Foo() : value(0) {} 

    boost::function<void (int&)> getFcn() 
    { 
     return boost::function<void (int&)>(boost::bind<void>(Foo::value, this, _1)); 
    } 

    int getValue() const { return value; } 

private: 
    int value; 
}; 

int main(int argc, const char * argv[]) 
{ 
    Foo foo; 

    std::cout << "Value before: " << foo.getValue(); 

    boost::function<void (int&)> setter = foo.getFcn(); 
    setter(10);  // ERROR: No matching function for call to object of type 'boost::function<void (int &)>' 
        // and in bind.hpp: Called object type 'int' is not a function or function pointer 

    std::cout << "Value after: " << foo.getValue(); 

    return 0; 
} 

Je vais avoir l'erreur sur la ligne 28, où je veux utiliser la fonction pour définir Foo :: valeur à 10. Suis-je juste aller dans toute cette affaire ne va pas? Devrais-je simplement retourner un int * ou quelque chose au lieu d'utiliser boost pour tout cela? La raison pour laquelle j'appelle 'getFcn()' est parce que dans mon projet actuel j'utilise un système de messagerie, et si l'objet avec les données que je veux n'est plus là, getFcn retournerait une fonction boost :: vide. Mais je suppose qu'avec un int * je pourrais juste retourner NULL si rien n'a été trouvé.

Répondre

2

Ce boost::bind<void>(Foo::value, this, _1) dans votre code utilise essentiellement Foo::value en tant que fonction membre. Ce qui est faux. Foo::value n'est pas une fonction.

Construisons cette étape par étape:

class Foo 
{ 
    ... 
    boost::function< void (Foo*, int) > getFcn() 
    { 
     return boost::function< void (Foo*, int) >(&Foo::setValue); 
    } 

    void setValue (int v) 
    { 
     value = v; 
    } 
    ... 
} 

int main() 
{ 
    ... 
    boost::function< void (Foo*, int) > setter = foo.getFcn(); 
    setter(&foo, 10); 
    ... 
} 

Voici donc la fonction prend this objet explicitement. Utilisons boost.bind pour lier this comme premier paramètre.

class Foo 
{ 
    ... 
    boost::function< void (int) > getFcn() 
    { 
     return boost::bind(&Foo::setValue, this, _1); 
    } 

    void setValue (int v) 
    { 
     value = v; 
    } 
    ... 
} 

int main() 
{ 
    ... 
    boost::function< void (int) > setter = foo.getFcn(); 
    setter(10); 
    ... 
} 

(code non testé)

+0

J'essaie d'éviter d'avoir une méthode setter dans la classe pour chaque variable que je veux faire pour. Je cherche un moyen de modifier la variable directement. Peut-on utiliser boost :: function de cette façon? –

+1

@NicFoster, je ne crois pas. Boost.Function est une enveloppe sur les choses qui se comportent comme des fonctions. Vous essayez de l'enrouler sur 'int'. – Vikas

+0

Assez juste, j'ai supposé que vous pourriez utiliser bind pour lier aux variables membres que vous seriez en mesure d'utiliser 'function' pour définir ces variables membres. –

Questions connexes