IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

SL & STL C++ Discussion :

[STL]Pointeur sur fonction membre (conversion avec mem_fun)


Sujet :

SL & STL C++

  1. #1
    Membre à l'essai
    Profil pro
    Étudiant
    Inscrit en
    Mars 2002
    Messages
    19
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2002
    Messages : 19
    Points : 11
    Points
    11
    Par défaut [STL]Pointeur sur fonction membre (conversion avec mem_fun)
    Bonjour

    Voici mon problème (qui n'est pas courant et après de nombreuses recherches infructueuses je me permet de poster ici) :

    j'ai une fonction dans une classe qui attend comme un argument un pointeur de fonction.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    typedef void (*pf)(X*, Y*); // la définition du pointeur de fonction (X et Y sont deux classes quelconques)
     
    class CControl;
    ...
     
    CControl::setFunction(pf uneFonction) // prend en argument un pointeur de fonction
    {
    ...
    }
    L'appel de cette fonction est le suivant :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
        AControl->setFunction(Form1->ControlEvent); // Form1->ControlEvent est une fonction correcte sauf qu'elle est dans une classe
    L'objet Form1 est de type CForm1 qui est une classe définit par l'utilisateur et comprend une fonction ControlEvent dont la signature correspond a pf
    (sauf que la fonction étant dans une classe ce n'est plus la même signature et la est le problème n'est-ce pas ?)

    La question est comment transformer cette fonction membre en une fonction pour être utilisé dans l'appel.

    En gros ça doit etre un peu comme dans la STL avec for_each quand on utilise mem_fun mais je ne comprend pas comment procéder.
    J'avais essayé l'appel comme ceci:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
        AControl->setFunction(mem_fun(&CForm1::Button1OnClick));
    et j'obtient le message d'erreur suivant : "Could not find a match for 'mem_fun<S,T,A>(void (CForm1::*)(X*,Y *))'"

    (Mon compilateur est Borland C++ 5.5 en ligne de commande sous windows XP.)

    J'espère avoir été clair (meme si j'en ai pas trop l'impression )
    Merci d'avance et n'hésitez pas à me demander des éclaircissements sur le code

  2. #2
    Membre averti
    Homme Profil pro
    Inscrit en
    Avril 2002
    Messages
    290
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Secteur : Industrie

    Informations forums :
    Inscription : Avril 2002
    Messages : 290
    Points : 325
    Points
    325
    Par défaut
    NON !

    mem_fun est concu pour etre utilise dans une fonction template... et il ne renvoie pas un pointeur de fonction mais au contraire une instance de classe mem_fun issue de temlate...

    ta methode dans CForm peut-elle etre static ? c'est une solution...

  3. #3
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2003
    Messages
    394
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2003
    Messages : 394
    Points : 473
    Points
    473
    Par défaut
    En première lecture, je pense que tu as simplement un problème de typage.
    Le type d'une fonction membre n'est pas le même que celui d'une fonction globale de même profil.
    Dans l'exemple suivant
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    struct A
    {
      void mem_foo() {}
    };
     
    void foo() {}
    Le type de foo est void (*) ()
    Le type de mem_foo est void (A::*)()
    Il n'est pas possible de transtyper l'un vers l'autre.

    Donc dans ton exemple, CControl::setFonction() attend un paramètre du type void (*) (*X,*Y). Or ce que tu lui fournit est de type void (Form1::*)(*X,*Y).
    Tu avais d'ailleurs l'intuition du problème. Le plus simple c'est de modifier le profil de CControl::setFonction() pour qu'il bosse avec le bon type de paramètre.

    Quant à mem_fun, ceci est une autre histoire...

  4. #4
    Rédacteur/Modérateur
    Avatar de JolyLoic
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2004
    Messages
    5 463
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2004
    Messages : 5 463
    Points : 16 213
    Points
    16 213
    Par défaut
    Je précise qu'à coup de boost::function et de boost::bind, tous les problèmes de ce genre sont aisément solubles, le seul problème est de pouvoir modifier le code qui utilise un callback :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    CControl::setFunction(boost::function<void (X*, Y*)>  uneFonction)
    {
    ...
    }
     
    AControl->setFunction(boost::bind(myForm1, &Form1::ControlEvent));
    Si on ne peut pas, la solution classique est de passer par une fonction intermédiaire qui réinterprète un de ses arguments comme un pointeur sur un classe sur laquelle elle va appeler la fonction membre.
    Ma session aux Microsoft TechDays 2013 : Développer en natif avec C++11.
    Celle des Microsoft TechDays 2014 : Bonnes pratiques pour apprivoiser le C++11 avec Visual C++
    Et celle des Microsoft TechDays 2015 : Visual C++ 2015 : voyage à la découverte d'un nouveau monde
    Je donne des formations au C++ en entreprise, n'hésitez pas à me contacter.

  5. #5
    Membre à l'essai
    Profil pro
    Étudiant
    Inscrit en
    Mars 2002
    Messages
    19
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2002
    Messages : 19
    Points : 11
    Points
    11
    Par défaut
    Merci pour vos réponses

    En effet VoidSeer je pense comprendre le problème fonction membre / fonction globale cependant je ne peux pas utiliser de fonctions globales .

    C'est pour cela que je pensais a mem_fun mais d'après Gandalf ce n'est pas possible.

    Et a votre avis est-ce que je peux changer la déclaration de CControl::setFunction pour pouvoir lui transmettre "une instance de classe mem_fun issue de temlate" ?

    PS : j'essaye avec static mais j'ai des problèmes.
    En gros je n'arrive plus a utiliser les objets dans la méthode statique.
    Message d'erreur : "Member cannot be used without an object in function"
    Quels sont les changements que static impliquent ?

  6. #6
    Membre à l'essai
    Profil pro
    Étudiant
    Inscrit en
    Mars 2002
    Messages
    19
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2002
    Messages : 19
    Points : 11
    Points
    11
    Par défaut
    Incroyable je poste et une réponse est arriver qui me semble répondre à ma question.

    Merci JolyLoic j'essaierai meme si le fait d'installer boost me rebute un peu,
    non pas que je considère cette bibliothèque comme peu performante (au contraire) mais j'aurais préféré tout faire en "C++ standard" avec la STL.

    A+

Discussions similaires

  1. Réponses: 3
    Dernier message: 20/02/2008, 16h29
  2. pbm pointeurs sur fonction membre :)
    Par overbreak dans le forum C++
    Réponses: 8
    Dernier message: 15/02/2008, 15h14
  3. [POO] Pointeur sur fonction membre et héritage
    Par MrDuChnok dans le forum C++
    Réponses: 9
    Dernier message: 20/07/2006, 17h19
  4. Pointeur sur fonction membre avec parametre
    Par Glosialabolas dans le forum C++
    Réponses: 7
    Dernier message: 06/02/2006, 02h32
  5. Réponses: 10
    Dernier message: 03/02/2005, 13h09

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo