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

C++/CLI Discussion :

Hastable String/pointeur de fonction


Sujet :

C++/CLI

  1. #1
    Membre régulier Avatar de Thor Tillas
    Inscrit en
    Octobre 2006
    Messages
    113
    Détails du profil
    Informations forums :
    Inscription : Octobre 2006
    Messages : 113
    Points : 90
    Points
    90
    Par défaut Hastable String/pointeur de fonction
    Hello,

    Je me demandais s'il était possible de faire une hashtable qui contiennent un pointeur de fonction.

    Le but serait de pouvoir appeler une fonction en fonction d'un string...

    j'ai essayé ca :

    header.h
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
     
    typedef void (*pointer_fct)();
     
    public ref class PrerollTest :ITest {
      private:
        System::Collections::Hashtable^ map;
     
      public:
        PrerollTest(TestManager^ p_testManager);
        ~PrerollTest();
        void run(String^ name);
     
     
        //Test Method Declaration
        void FileSourceToWindowsDest();
      };
    code.cpp
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
     
    PrerollTest::PrerollTest(TestManager^ p_testManager)
    {
       //Create the map to store the function pointer and is name
      this->map = gcnew System::Collections::Hashtable();
     
      //get the string
      String^ s = "File Source To Windows Dest";
     
     //Add the function pointer into the map
      this->map->Add(s,this->FileSourceToWindowsDest);
    }
     
    PrerollTest::~PrerollTest()
    {
     
    }
     
     
    /*****************************************
    * Virtual method declaration
    *****************************************/
    void PrerollTest::run(String^ name)
    {
      //name is the name of the pointer function that we want to launch
     
      bool runAll;
      if(name->Equals("Run all"))
      {
        for each(*pointer_fct p in map->Values)
        {
          p();
         }
      }
    else
      {
        System::Collections::IDictionaryEnumerator^ e = map->GetEnumerator();
        while ( e->MoveNext() )
          if(e->Key->Equals(name))
          {
            *pointer_fct p = e->Value;
            p();
          }
     
      }
     
    }
     
    /******************************************
    * fonction 
    ******************************************/
    void PrerollTest::FileSourceToWindowsDest()
    {
    }
    Je trouve rien sur le net et je sèche pas mal sur comment résoudre ce problème... une solution serait d'utiliser la map<string *, pointer_fct> de std mais je voulais rester en CLI pour faire ca...

    Si vous avez une idée ou repéré une erreur ou eu plus de chance que moi lors de vos recherche... bref... merci d'avance
    Au travail, il y a deux sortes de personnes. Ceux qui ont un pistolet chargé, et ceux qui creusent. Moi je creuse...

  2. #2
    Rédacteur
    Avatar de nico-pyright(c)
    Profil pro
    Inscrit en
    Octobre 2003
    Messages
    6 414
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2003
    Messages : 6 414
    Points : 16 075
    Points
    16 075
    Par défaut
    quel est le problème ?
    ca devrait marcher
    mais tu as tout à fait interet à utiliser les delegate si tu veux rester conforme CLS

  3. #3
    Membre régulier Avatar de Thor Tillas
    Inscrit en
    Octobre 2006
    Messages
    113
    Détails du profil
    Informations forums :
    Inscription : Octobre 2006
    Messages : 113
    Points : 90
    Points
    90
    Par défaut
    ok... dsl pour le dérangement, c'était pas si compliquer que ca finalement... j'ai un peu mieux regarder les erreurs du compilo et remplacer mes pointeurs de fonction par des delegate...

    Ca compile (je sais pas si ca marche... pas encore fait la partie qui devrait tester ca ^^)...

    Donc pour ceux que ca intéresse, le code donne ca :

    header.h
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
     
    private delegate void testFunction();
     
      public ref class PrerollTest :ITest {
      private:
        System::Collections::Hashtable^ map;
     
      public:
        PrerollTest(TestManager^ p_testManager);
        ~PrerollTest();
        virtual void run(System::String^ name) override;
     
        //Test Method Declaration
        void FileSourceToWindowsDest();
      };
    code.ccp
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
     
    PrerollTest::PrerollTest(TestManager^ p_testManager)
    {
      //Create the list to store the name of each test
      this->map = gcnew System::Collections::Hashtable();
     
      //Store in the Hashmap the function pointer and the string
      //get the string
      String^ s = "File Source To Windows Dest";
      //Add the test into the map
      testFunction^ ftow = gcnew testFunction(this, &PrerollTest::FileSourceToWindowsDest);
      this->map->Add(s,ftow);
     
    }
     
     
    PrerollTest::~PrerollTest()
    {
     
    }
     
     
    /*****************************************
    * Virtual method declaration
    *****************************************/
    void PrerollTest::run(String^ name)
    {
      if(name->Equals("Run all"))
      {
        for each(testFunction^ p in map->Values)
          p();
      }else
      {
        System::Collections::IDictionaryEnumerator^ e = map->GetEnumerator();
        while ( e->MoveNext() )
          if(e->Key->Equals(name))
          {
            ((testFunction^)e->Value)();
     
          }
     
      }
    }
     
     
    void PrerollTest::FileSourceToWindowsDest()
    {
    }

    Merci pour l'info sur les delegate... je connaissais pas ce type... bien pratique en tout cas
    Au travail, il y a deux sortes de personnes. Ceux qui ont un pistolet chargé, et ceux qui creusent. Moi je creuse...

  4. #4
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 519
    Points
    41 519
    Par défaut
    Si tu es en C++/CLI, tu es donc en .Net 2.0.
    Pourquoi ne pas utiliser des Dictionary<> ?
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  5. #5
    Membre régulier Avatar de Thor Tillas
    Inscrit en
    Octobre 2006
    Messages
    113
    Détails du profil
    Informations forums :
    Inscription : Octobre 2006
    Messages : 113
    Points : 90
    Points
    90
    Par défaut
    euh... parce que je sais pas ce que c'est ?^^ je me renseigne et je te dis pourquoi je vais pas l'utiliser ou pourquoi tu viens de me sauver la vie, ma place et ma famille
    Au travail, il y a deux sortes de personnes. Ceux qui ont un pistolet chargé, et ceux qui creusent. Moi je creuse...

  6. #6
    Membre régulier Avatar de Thor Tillas
    Inscrit en
    Octobre 2006
    Messages
    113
    Détails du profil
    Informations forums :
    Inscription : Octobre 2006
    Messages : 113
    Points : 90
    Points
    90
    Par défaut
    Apparement, je pourrais utilisé l'un ou l'autre.
    L'objet dictionnaire permet de retrouver plus facilement un objet qu'il contient que les autres objets collections (cf cours d'algorithmique d'il y a deux ans... ouf c'est loin tout ca) et donc parait en effet plus indiqué dans ce cas présent.

    Je n'ai pas très bien compris cette partie par contre :
    Ce dernier [l'objet Collection] est utile dans certaines situations où l'objet Dictionary ne l'est pas. Par exemple, si vous créez un modèle objet personnalisé, l'objet Collection permet de stocker la référence d'une collection personnalisée, mais non l'objet Dictionary.
    Cela veut-il dire que Dictionary ne peut pas stocker de référence vers un objet autre que ceux défini par MS (genre autre que String, List, Forms etc) ou ca veut dire que l'on ne peut pas créer son propre dictionnaire et le référencer... pas très clair je trouve

    Si c'est la première idée... ben c'est vachement ridicule comme Structure de donnée... pas pouvoir référencer nos propres objet empêche plus de la moitié des utilisations

    Si c'est la seconde idée... je vois pas trop comment ca se fait...

    J'imagine donc qu'il doit y avoir une autre explication à ce bout de texte...



    [EDIT] Au fait pour ceux qui sont intéressé par le bout de code poster ben il fonctionne^^ j'ai testé ca hier...
    Au travail, il y a deux sortes de personnes. Ceux qui ont un pistolet chargé, et ceux qui creusent. Moi je creuse...

  7. #7
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 519
    Points
    41 519
    Par défaut
    C'est faux, Dictionary permet de stocker tout ce que tu veux, même d'autres collections génériques (même si Billou le déconseille).
    Tu peux même te faire un Dictionary de Object si ça te chante...

    Où as-tu lu cette phrase en Français ?
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  8. #8
    Membre régulier Avatar de Thor Tillas
    Inscrit en
    Octobre 2006
    Messages
    113
    Détails du profil
    Informations forums :
    Inscription : Octobre 2006
    Messages : 113
    Points : 90
    Points
    90
    Par défaut
    sur MSDN France ... euh ce lien je crois : http://msdn.microsoft.com/library/fr...naryobject.asp
    Au travail, il y a deux sortes de personnes. Ceux qui ont un pistolet chargé, et ceux qui creusent. Moi je creuse...

  9. #9
    Membre régulier Avatar de Thor Tillas
    Inscrit en
    Octobre 2006
    Messages
    113
    Détails du profil
    Informations forums :
    Inscription : Octobre 2006
    Messages : 113
    Points : 90
    Points
    90
    Par défaut
    Voici donc le même code mais modifier pour utiliser un dictionaire de type :

    System::Collection::Generic:ictionary<String^, delegate^> où delegate doit être remplacer par le nom de votre fonction delegate (dans mon cas testFunction)

    En espérant que ca puisse servir à quelqu'un un de ces jours ^^

    Donc il y a deux méthode, une qui sert à lancer les fonction delegate stocké dans le dico et une autre qui renvoi une liste avec le nom de toutes les méthodes stockée...


    header.h

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
     
     
    private delegate void testFunction();
     
      public ref class PrerollTest :PrerollTest {
      private:
        System::Collections::Dictionary<String^,testFunction^>^ dico;
     
      public:
        PrerollTest ();
        ~PrerollTest ();
        virtual void run(System::String^ name) ;
        virtual System::Collection::Generic::List^<String^> getAllName();
     
        //Test Method Declaration
        void aTestFunction();
      };
    code.ccp

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
     
     
    PrerollTest::PrerollTest ()
    {
      //Create a dictionary to store the name of each test and his function
      this->dico= gcnew System::Collections::Dictionary<String^,testFunction^>();
     
      //Store in the Dicotionary the function pointer and the string
      //get the string
      String^ s = "A test Function";
      //Add the test into the dico
      testFunction^ aDelegate = gcnew testFunction(this, &PrerollTest::aTestFunction);
      this->dico->Add(s,aDelegate);
     
    }
     
     
    PrerollTest::~PrerollTest ()
    {
     
    }
     
     
    void PrerollTest::run(String^ name)
    {
    //if the name is Run all -> just take each test and launch it
      if(name->Equals("Run all"))
      {
        for each(KeyValuePair<String^, testFunction^> ksp in dico)
          ksp.Value();
     
      }else
      {
    //else try to find the right test and launch it
        testFunction^ value;
        if(dico->TryGetValue(name, value))
          value();
      }
     
    }
     
    List<String^>^ PrerollTest::getAllTest()
    {
      List<String^>^ list = gcnew List<String^>();
      for each(KeyValuePair<String^, testFunction^> ksp in dico)
        list->Add(ksp.Key);
      return list; 
    }
     
     
    void PrerollTest::aTestFunction()
    {
    }
    Au travail, il y a deux sortes de personnes. Ceux qui ont un pistolet chargé, et ceux qui creusent. Moi je creuse...

  10. #10
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 519
    Points
    41 519
    Par défaut
    Euh...
    C'est pour VBScript ou VBA, ton lien.
    Je ne pense pas qu'il s'agisse du Dictionary .Net...
    Surtout que les méthodes "en plus" mentionnées n'existent pas dans un Dictionary .Net...
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  11. #11
    Membre régulier Avatar de Thor Tillas
    Inscrit en
    Octobre 2006
    Messages
    113
    Détails du profil
    Informations forums :
    Inscription : Octobre 2006
    Messages : 113
    Points : 90
    Points
    90
    Par défaut
    ok je comprends mieux... en effet j'avais pas vu ca sous cette angle... ca explique pourquoi je comprennais vraiment rien en tout cas.

    En attendant, je suis pas trop sur de voir une grosse différence entre Dico et Hashtable... Malgré que mes souvenirs d'algorithmique me pousse à dire que le dico est plus rapide en recherche... je dois dire que je sais pas trop dans quel cas je dois utilisé plutot un ou plutot l'autre.

    En gros, pour moi, j'utilise le dico sur les clé String ou Object et le hastable sur les clé int et autre.

    Si tu as le temps de me donner une ou deux précision sur les différences je suis évidemment preneur

    Sinon, je chercherais encore quelques info sur msdn et autre...
    Au travail, il y a deux sortes de personnes. Ceux qui ont un pistolet chargé, et ceux qui creusent. Moi je creuse...

  12. #12
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 519
    Points
    41 519
    Par défaut
    La grosse différence, c'est surtout que Dictionary<> est fortement typé contrairement à HashTable...
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  13. #13
    Membre régulier Avatar de Thor Tillas
    Inscrit en
    Octobre 2006
    Messages
    113
    Détails du profil
    Informations forums :
    Inscription : Octobre 2006
    Messages : 113
    Points : 90
    Points
    90
    Par défaut
    En gros Hastable est à utiliser lorsque l'on sait que l'on va avoir plusieurs type d'objet dans la même collection et Dictionnaire lorsque tous les couples clé/valeur sont de même type...

    J'ai tout compris ?
    Au travail, il y a deux sortes de personnes. Ceux qui ont un pistolet chargé, et ceux qui creusent. Moi je creuse...

  14. #14
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 519
    Points
    41 519
    Par défaut
    Ben non, HashTable est à ne pas utiliser du tout.
    Tu peux toujours faire un Dictionary de Object si tu veux...

    Et puis, la clé d'un dictionnaire est rarement hétérogène, elle...
    Et il est encore plus rare que les deux types à la fois soient hétérogènes.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 5
    Dernier message: 17/05/2007, 18h12
  2. Declaration de fonction retournant un pointeur sur fonction
    Par pseudokifaitladifférence dans le forum C
    Réponses: 5
    Dernier message: 11/08/2003, 19h37
  3. Matrice de pointeurs de fonctions
    Par sebduth dans le forum C
    Réponses: 15
    Dernier message: 18/07/2003, 14h03
  4. [Kylix] Pointeur de fonctions
    Par _dack_ dans le forum EDI
    Réponses: 1
    Dernier message: 03/07/2003, 10h17
  5. pointeur de fonction
    Par kardath dans le forum C
    Réponses: 4
    Dernier message: 28/12/2002, 14h39

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