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# Discussion :

changer dynamiquement le corps d'une méthode


Sujet :

C#

  1. #1
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    69
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 69
    Points : 30
    Points
    30
    Par défaut changer dynamiquement le corps d'une méthode
    Dans mon assembly (qui est chargé en mémoire), j'ai la classe suivante :
    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
     
            public class myString
            {
                private string _s;
     
                public myString(string s)
                {
                    _s = s;
                }
     
                public void uneFonction()
                {
                    Console.WriteLine("V1"+_s);
                }
            }
    DOnc quand je fais
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    myString myS = new myString("toto");
    myS.uneFonction();
    j'obtiens : V1toto


    Je voudrais pouvoir dynamiquement changer le code de uneFonction. (Par exemple afficher V2+_s). En regardant du coté de la réflection j'ai trouvé des trucs sympatiques mais rien de concluant. Est ce que d'après vous cela est faisable et comment?

  2. #2
    Expert confirmé

    Homme Profil pro
    Chef de projet NTIC
    Inscrit en
    Septembre 2006
    Messages
    3 580
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Chef de projet NTIC
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Septembre 2006
    Messages : 3 580
    Points : 5 195
    Points
    5 195
    Par défaut
    salut

    Deux approches possibles, ton exemple étant tres simple, on pourrait
    envisager que ta classe possède un parametre String en libre accès pour modifier par exemple V1 en V2....

    Maintenant, tu peux aussi passer par la technologie des "plug-in"... à savoir,
    définir une interface que tes plug-ins doivent implémenter.. et ensuite, à chaque
    fois que tu as un nouveau plug-in, tu instancies les méthodes appropriés et tu peux charger dynamiquement ce plug-in.. etc, etc...

    Autre solution envisageable, utiliser CSharpCodeProvider pour compiler en mémoire (ou sous forme de dll) le code que tu dois utiliser et ensuite, l'appeler
    via le point d'appel que t'auras fourni CSharCodeProvider

    Voila les 3 solutions que j'envisagerais pour un tel problème

    The Monz, Toulouse
    The Monz, Toulouse
    Expertise dans la logistique et le développement pour
    plateforme .Net (Windows, Windows CE, Android)

  3. #3
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Septembre 2007
    Messages
    27
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2007
    Messages : 27
    Points : 33
    Points
    33
    Par défaut
    Salut, regarde du côté du namespace System.Reflection.Emit du msdn (surtout les méthodes dynamiques) : tu peux emettre du code MSIL pour faire évoluer tes classes dynamiquement.

    Sinon tu as le pattern 'décorateur', côté conception. Tout dépend de ce dont tu as besoin exactement.

    Ceci dit il est rare d'avoir à se servir de tout ça ; tu as reellement besoin que ce soit la même méthode, avec la signature identique, d'une même classe (pas un type hérité) qui évolue ? C'est plus que rare, comme besoin.

  4. #4
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    69
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 69
    Points : 30
    Points
    30
    Par défaut
    Bon c'est vrai que j'ai pris un exemple relativement simple et qui du coup ne reflete peu etre pas totalement ma problématique.

    En rentrant un peu plus dans les détails, je voudrais pouvoir modifier pendant l'éxécution de mon programme le comportement de uneFonction.
    i-lancement du prog
    ii-Initialement myS.uneFonction(); affiche "V1+_s".
    iii-pendant l'éxécution, je me dit tiens cela serait bien si, finalement, lorsque'un objet de type myString appelle uneFonction alors il affiche _s+_s.

    ex:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    myString myS = new myString("toto");
    myS.uneFonction(); //affiche V1toto
     
    //ici je fais ce qu'il faut...
     
    myS.uneFonction();//affiche totototo

    Je pense que ta troisième réponse (CSharCodeProvider ) peut permettre cela. Mais je me demande comment faire pour:
    1-"compléter" la classe myString en lui ajoutant la nouvelle focntion
    2-lorsqu'il y a un appel à uneFonction (la méthode initiale), alors c'est la seconde version qui est appelé
    3-comment la seconde version de la fonction peut-elle connaitre le champs _s ?

  5. #5
    Membre expert
    Avatar de hed62
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Juillet 2007
    Messages
    2 029
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Développeur .NET
    Secteur : Santé

    Informations forums :
    Inscription : Juillet 2007
    Messages : 2 029
    Points : 3 134
    Points
    3 134
    Par défaut
    Avant tout, regarde ces deux design pattern :

    - Stratégie : te permet de "brancher" et "débrancher" lors de l'exécution, des comportements prévus à l'avance

    - Décorateur : permet d'ajouter du comportement à l'exécution

    Dans les deux cas les comportements doivent être prévus.

    Si ce n'est pas ton but, la création et la compilation de code à la volée avec CSharpCodeProvider sera indispensable.
    Hervé Delannoy, Ingénieur études&développement.

    Je n'accepte pas les demandes de mise en relation MSN/yahoo sans motif.
    ------------------------------------------------------------------------
    Si , ni , ne peuvent vous aider, mais nous oui, pensez à un pti et au !
    Merci de vous relire
    ____________________________________________________________________________________
    Recherche joueurs de "Magic" sur Lille et environs.
    Donner plutôt que jeter.

  6. #6
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    69
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 69
    Points : 30
    Points
    30
    Par défaut
    Avant tout, regarde ces deux design pattern :

    - Stratégie : te permet de "brancher" et "débrancher" lors de l'exécution, des comportements prévus à l'avance

    - Décorateur : permet d'ajouter du comportement à l'exécution

    Dans les deux cas les comportements doivent être prévus.

    Si ce n'est pas ton but, la création et la compilation de code à la volée avec CSharpCodeProvider sera indispensable.
    Le comportement n'est pas prévu, l'utilisateur tape à la main le nouveau corps de la fonction.

    CSharpCodeProvider me permet de créer des classes à aprtir de zéro mais je n'arrive pas modifier une classe présente (pex lui ajouter une nouvelle méthode ou modifier le comporetemetn d'une méthode existante)...

  7. #7
    Membre expert
    Avatar de hed62
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Juillet 2007
    Messages
    2 029
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Développeur .NET
    Secteur : Santé

    Informations forums :
    Inscription : Juillet 2007
    Messages : 2 029
    Points : 3 134
    Points
    3 134
    Par défaut
    Alors combine "stratégie" et CSharpCodeProvider :

    La classe centrale et immuable contient une instance d'une autre classe qui elle implémente une interface ne disposant que d'une méthode, ma_fonction().

    Ca c'est stratégie.

    Avec CSharpCodeProvider, tu écris une de ces stratégie, qui implémentera "ma_fonction" avec le code de l'utilisateur.

    Ensuite, tu charge le code de cette classe, et l'associe avec la classe centrale.

    Ainsi, tu auras :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    class ClasseCentrale
    {
     private IStrategie strategie;
    // cstr, getter, setter, etc...
     
    public void ma_fonction()
    {
     strategie.ma_fonction();
    }
    }
    Hervé Delannoy, Ingénieur études&développement.

    Je n'accepte pas les demandes de mise en relation MSN/yahoo sans motif.
    ------------------------------------------------------------------------
    Si , ni , ne peuvent vous aider, mais nous oui, pensez à un pti et au !
    Merci de vous relire
    ____________________________________________________________________________________
    Recherche joueurs de "Magic" sur Lille et environs.
    Donner plutôt que jeter.

  8. #8
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    69
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 69
    Points : 30
    Points
    30
    Par défaut
    hed62> ok mais comment faire pour que le code de la classe implémentant IStartégie ai acces aux membres de ma classe centrale. Pour revenir à l'xemple simple que j'avais donné, comment faire pour que la méthode ma_fonction de la nouvelle classe est acces au champs _s ?
    (RQ : si l'ont fait dérivé la nouvelle classe de la classe centrale on aura bien acces au chaps _s mais se serait le champs d'un tout autre objet !)

  9. #9
    Membre expert
    Avatar de hed62
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Juillet 2007
    Messages
    2 029
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Développeur .NET
    Secteur : Santé

    Informations forums :
    Inscription : Juillet 2007
    Messages : 2 029
    Points : 3 134
    Points
    3 134
    Par défaut
    Il te faut passer les informations utiles en paramètre.

    Cela peut etre une simple string, un "object", une reference à ClasseCentrale, ou carément un object[], ou une HashTable...

    Mais dans ce cas, cela modifie l'appel à ma_fonction et ca complique bien les choses...
    Hervé Delannoy, Ingénieur études&développement.

    Je n'accepte pas les demandes de mise en relation MSN/yahoo sans motif.
    ------------------------------------------------------------------------
    Si , ni , ne peuvent vous aider, mais nous oui, pensez à un pti et au !
    Merci de vous relire
    ____________________________________________________________________________________
    Recherche joueurs de "Magic" sur Lille et environs.
    Donner plutôt que jeter.

  10. #10
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    69
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 69
    Points : 30
    Points
    30
    Par défaut
    Mais dans ce cas, cela modifie l'appel à ma_fonction et ca complique bien les choses...
    Disons que cela ne me convient pas vraiment car je ne voudrait pas à avoir a passer tous ces objets en paramètre, c'est un peu trop de la bidouille..

    Un peu dans l'idée de la stratégie on pourrait faire quelque chose dans le genre :
    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 monDelegate();
     
    class ClasseCentrale
    {
        private monDelegate d;
     
        public void callCurrentStrategie()
        {
            d();
        }
     
        public void strategie1()
        {
             //code
        }
    }
    Avec la variable d initialisé à strategie1. Après il "suffit" d'ajouter une méthode à classe centrale (via System.Reflection.Emit ??) et de la brancher sur d...Est ce que cette idée peu déboucher ?

  11. #11
    Membre expert
    Avatar de hed62
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Juillet 2007
    Messages
    2 029
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Développeur .NET
    Secteur : Santé

    Informations forums :
    Inscription : Juillet 2007
    Messages : 2 029
    Points : 3 134
    Points
    3 134
    Par défaut
    Oui, ca peut. Mais tu auras quand même des soucis quand tu voudras passer d'autres infos. Informe moi de ton avancement, ca m'interresse
    Hervé Delannoy, Ingénieur études&développement.

    Je n'accepte pas les demandes de mise en relation MSN/yahoo sans motif.
    ------------------------------------------------------------------------
    Si , ni , ne peuvent vous aider, mais nous oui, pensez à un pti et au !
    Merci de vous relire
    ____________________________________________________________________________________
    Recherche joueurs de "Magic" sur Lille et environs.
    Donner plutôt que jeter.

  12. #12
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    69
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 69
    Points : 30
    Points
    30
    Par défaut
    Je viens de penser à quelque chose : ne pourrait-on pas naviguer entre deux domaines d'applications avec des versions différents des fonctions ? Je verrais le scénario suivant :

    1-chargement initial des assembly dans domaine1
    2-fonctionnement du prog dans domaine1, je garde un accès direct à tous les obejts utilisés
    3-je change le corps d'une fonctions
    4-recompilation du tout
    5-chargement dans domaine2
    6-je "pause" le domaine1
    7-transfert de tous les objets dans domaine2 (normalement possible vu que j'ai charger les memes dll)
    8-reprise (normalement les objets devrait utiliser la nouvelle version de la méthdoe, non?)


    Je ne sais pas trop comment marche les dommaine d'application, c'est une idée comme ca...

Discussions similaires

  1. Réponses: 1
    Dernier message: 12/09/2007, 18h11
  2. Réponses: 1
    Dernier message: 29/08/2006, 12h01
  3. Réponses: 2
    Dernier message: 21/07/2006, 06h55
  4. Réponses: 3
    Dernier message: 31/08/2005, 17h52
  5. Comment changer dynamiquement la valeur d'une option de DbGrid ?
    Par Atrebate62 dans le forum Composants VCL
    Réponses: 4
    Dernier message: 17/03/2005, 13h35

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