GNT sans publicité, site mobile, fonctionnalitées exclusives...

Hierarchie de message et de target

Le
amerio
Bonjour,
Je cherche a implémenter un système de message/target supportant héritage.
Dans le principe : on a une hiérarchie de Message, et une hiérarchie de Target acceptant
certains Message.

class Message { } // classe de base
class MessageSpecial : public Message { }
class MessageSpecialExt : public MessageSpecial { }

La classe de base des Target doit ressembler à ca :
class Target
{
Target();
virtual ~Target();
virtual bool OnMessage(Message& msg); // le point de reception public

protected:
virtual bool HandleMessage(Message& msg); // traitement du msg de base
}

Ce dont j'ai besoin :
class TargetSpecial : public Target
{
TargetSpecial();
virtual ~TargetSpecial();

protected:
virtual bool HandleMessageSpecial(MessageSpecial& msg);
}

A noter que je *veux* éviter d'avoir HandleMessageSpecial(Message& msg)
(pour éviter un cast a chaque fois, et c'est ça qui est dur)

J'ai vu l'exemple de Meyers dans More Effective C++, mais il est inapplicable pour moi :
- ça oblige a faire un cast (et je veux éviter) : HandleMessageSpecial(Message& msg)
- l'utilisation d'une map ne permet pas de gérer une hiérarchie de message (si j'ajoute
une nouveau message mais pas de handler associé, il sera ignorer et non traité, car non
trouvé dans le map)

J'ai perdu ma journée la dessus, alors toute idée est bienvenue.
Lire les 15 réponses

Vidéos High-Tech et Jeu Vidéo
Téléchargements
Vos réponses Page 1 / 3
Gagnez chaque mois un abonnement Premium avec GNT : Inscrivez-vous !
Trier par : date / pertinence
Christophe Lephay
Le #69311
amerio wrote:
Bonjour,
Je cherche a implémenter un système de message/target supportant
héritage.
Dans le principe : on a une hiérarchie de Message, et une hiérarchie
de Target acceptant certains Message.

class Message { ... } // classe de base
class MessageSpecial : public Message { ... }
class MessageSpecialExt : public MessageSpecial { ... }

La classe de base des Target doit ressembler à ca :
class Target
{
Target();
virtual ~Target();
virtual bool OnMessage(Message& msg); // le point de reception
public

protected:
virtual bool HandleMessage(Message& msg); // traitement du msg
de base }

Ce dont j'ai besoin :
class TargetSpecial : public Target
{
TargetSpecial();
virtual ~TargetSpecial();

protected:
virtual bool HandleMessageSpecial(MessageSpecial& msg);
}

A noter que je *veux* éviter d'avoir HandleMessageSpecial(Message&
msg) (pour éviter un cast a chaque fois, et c'est ça qui est dur)


class Message
{
public:
virtual bool notify( Target * the_target ) { return
the_target->HandleMessage( *this ); } // *this est de type Message
};

class MessagePasSpecial : public Message
{
public:
// on ne redéfinit pas notify si on veut que HandleMessage( Message& ) gère
le message
};

class MessageSpecial : public Message
{
public:
bool notify( Target * the_target ) { return the_target->HandleMessage(
*this ); } // *this est de type MessageSpecial
};

class Target
{
public:
virtual bool HandleMessage( Message& );
};

class TargetSpecial : public Target
{
public:
virtual bool HandleMessage( MessageSpecial& );
};

Ensuite, pour gérer un message :

TargetSpecial ts;
Message * msg = GetNextMessage();
msg->notify( &ts );

Si msg pointe vers un MessageSpecial, notify devrait appeler
TargetSpecial::HandleMessage( MessageSpecial& ). Si il pointe vers un
Message ou MessagePasSpecial, notify appelle TargetSpecial::HandleMessage(
Message& )...

J'ai pas testé, et en plus il est tard. Si je suis à coté de la plaque, fais
des recherches sur double dispatch (ou pattern visitor), puisqu'il me semble
que c'est celà que tu veux. Note qu'en même temps, c'est ce dont parle
Meyers à ce qu'il me semble aussi...

Demain, il y fera plus clair :)

Chris

Christophe Lephay
Le #69310
Christophe Lephay wrote:
Je cherche a implémenter un système de message/target supportant
héritage.
Dans le principe : on a une hiérarchie de Message, et une hiérarchie
de Target acceptant certains Message.
...


A noter que je *veux* éviter d'avoir HandleMessageSpecial(Message&
msg) (pour éviter un cast a chaque fois, et c'est ça qui est dur)


class Message
{
public:
virtual bool notify( Target * the_target ) { return
the_target->HandleMessage( *this ); } // *this est de type Message
};

class MessagePasSpecial : public Message
{
public:
// on ne redéfinit pas notify si on veut que HandleMessage( Message&
) gère le message
};

class MessageSpecial : public Message
{
public:
bool notify( Target * the_target ) { return the_target->HandleMessage(
*this ); } // *this est de type MessageSpecial
};
...

Demain, il y fera plus clair :)


Sans attendre demain, je vois que mon code est à coté de la plaque...

Je ré-essaie demain (à priori, il faut une hiérarchie supplémentaire si on
veut pas de casts)..

Chris


Fabien LE LEZ
Le #69015
Tu peux peut-être essayer d'aller voir du côté des templates :

template <class Msg> class TargetT: virtual public Target
{
virtual bool HandleMessage(Message& msg)
{
return HandleMessageSpecial (dynamic_cast<Msg&>(msg));
};
virtual bool HandleMessageSpecial (Msg& msg);
};

class TargetSpecial : public TargetT<MessageSpecial>
{
bool HandleMessageSpecial (MessageSpecial& msg);
};


--
;-)
Christophe Lephay
Le #68412
Fabien LE LEZ wrote:
Tu peux peut-être essayer d'aller voir du côté des templates :

template <class Msg> class TargetT: virtual public Target
{
virtual bool HandleMessage(Message& msg)
{
return HandleMessageSpecial (dynamic_cast<Msg&>(msg));
};
virtual bool HandleMessageSpecial (Msg& msg);
};

class TargetSpecial : public TargetT<MessageSpecial>
{
bool HandleMessageSpecial (MessageSpecial& msg);
};


Mais ça se complique si on veut qu'un Target gère plusieurs types différents
de messages. Je crois que c'est ce que veut faire Amerio.

Borland et Microsoft définissaient des tas de macros pour arriver à celà...

Chris

Fabien LE LEZ
Le #68407
On Mon, 3 Nov 2003 11:47:06 +0100, "Christophe Lephay"

class TargetSpecial : public TargetT<MessageSpecial>
{
bool HandleMessageSpecial (MessageSpecial& msg);
};


Mais ça se complique si on veut qu'un Target gère plusieurs types différents
de messages.


class TargetVraimentSpecial : public TargetT<AutreMessageSpecial>,
public TargetSpecial
{
bool HandleMessageSpecial (AutreMessageSpecial& msg);
bool HandleMessageSpecial (MessageSpecial& msg);
};

Un peu lourd à écrire il est vrai...


Publicité
Suivre les réponses
Poster une réponse
Anonyme