Héritage de classe et vector - C++ - Programmation
Marsh Posté le 09-12-2003 à 00:16:16
Je vais sans doute dire une grosse connerie :
un "cast" explicite, ça ne marche pas ?
Marsh Posté le 09-12-2003 à 00:19:46
std::vector<animal*>
en C++, le polymorphisme passe par les pointeurs ou les références.
mais c'est quoi cette psychose des casts, c'est les fêtes qui vous font ça ou quoi? déjà que vous castez quand c'est inutile, voulez caster quand on ne peut pas. réfléchissez une peu sur ce que ça veut dire "caster" et pensez au types.
Marsh Posté le 09-12-2003 à 00:19:47
Non j'ai essayé et puis j'y tiens pas trop au "cast" ca va être plus que crade si il faut que je caste à chaque fois que je veux lire une propriété qui n'est pas dans "animal"
Marsh Posté le 09-12-2003 à 00:21:44
ben y a pas besoin de cast
si
*v[0] est un chien, et *v[1] un chat
v[0]->crie() -> "Ouaf"
v[1]->crie() -> "Miaou"
Marsh Posté le 09-12-2003 à 00:25:17
Taz a écrit : ben y a pas besoin de cast |
je comprends pas ca passe pas, en fait j'ai une propriété "taille" qui n'éxiste que dans la classe "tortue" et pas dans "chien" ni "animal" et je n'arrive pas à y accéder...
Marsh Posté le 09-12-2003 à 00:26:36
ben là il faut caster vie un dynamic_cast. si tu utilises des propriétés personnelle à la tortue, il faut que ton objet soit une tortue et typé tel quel
Marsh Posté le 09-12-2003 à 00:29:30
Taz a écrit : ben là il faut caster vie un dynamic_cast. si tu utilises des propriétés personnelle à la tortue, il faut que ton objet soit une tortue et typé tel quel |
Ok donc ca semble assez bancal comme facon de faire...
Comment ferais-tu pour classer dans un tableau des objets qui sont hérités de la même classe de base mais dont certaines propriétés ou méthodes sont personnelles et sans que cela soit trop infame comme solution ?
Marsh Posté le 09-12-2003 à 00:36:04
ça l'est pas du tout !
si tu fais de la généricité, tu considères des propriétés génériques, si tu veux quelque chose de spécifique, il faut retrouver cette spécifité.
L'exemple célèbre de Stroustrup, c'est les Saab : une 900 et une 90 : un voiture et un avion. c'est des Saab, pas de problèmes, y a des propriétés commune. Maintenant, si tu prends la peine de t'assurer que telle Saab est bien une voiture, je te laisse imaginer ce qui se passe tu tente de la faire décoler
Marsh Posté le 09-12-2003 à 00:40:42
Taz a écrit : ça l'est pas du tout ! |
Ok bon tant que ca te semble bien alors pourquoi pas
Je vais essayer de voir ca d'un peu plus près, merci.
Marsh Posté le 09-12-2003 à 01:34:14
Taz a écrit : ben là il faut caster vie un dynamic_cast. si tu utilises des propriétés personnelle à la tortue, il faut que ton objet soit une tortue et typé tel quel |
Marsh Posté le 09-12-2003 à 21:07:04
rajoute un membre à ta classe qui indique le type, pour retrouver tes spécialités
Code :
|
Marsh Posté le 09-12-2003 à 21:09:03
BlackGodess > droit dans le mur ! si on a inventé les RTTi, c'est justement pour pas avoir à écrire de genre de chose.
devine quoi, si le dynamic_cast<chien*> échoue, c'est àd ire que animaux[i] n'est pas une sort de chien, et bien le résultat vaut 0 (NULL) magique ?
Marsh Posté le 09-12-2003 à 21:10:20
ah ? j'avais vu qu'il y avait une sécuritée supplémentaire entre le dynamic_cast et le static_cast, mais c'est donc a l'execution ?
bien, désolé pour les anneries
Marsh Posté le 09-12-2003 à 21:13:01
static_cast -> transtypage sur, fonctionnel à la compilation, pas d'erreur. du genre chien* -> animal*
dynamic_cast -> non sur, nécessite des information de types dynamique, genre animal* -> chien* (et oui, impossible de savoir à la compilation si un animal est effectivement un chien). évidemment, on peut vérifier la réussite du transtypage, sinon ça n'a pas d'intéret)
Marsh Posté le 11-12-2003 à 23:41:50
Taz a écrit : BlackGodess > droit dans le mur ! si on a inventé les RTTi, c'est justement pour pas avoir à écrire de genre de chose. |
Taz, donc dans ce cas, il faudrait d'abord faire un test prealable quand meme sur le dynamic_cast non ??
Style
Code :
|
Il y a plus elegant ?
Marsh Posté le 11-12-2003 à 23:44:37
moi je trouve pas si moche que ça (sauf tes parenthèse superflues)
évidemment, si on travaille avec des références, le try/catch est plus attractif.
Marsh Posté le 11-12-2003 à 23:51:10
tu peux faire comme ça sinon
Code :
|
Marsh Posté le 13-12-2003 à 19:42:44
Toujours une histoire d'animaux .. polymorphiques ??
Supposons que je veuille reconstruire un animal a partir de son etat-civil qui va donc m'indiquer si c'est une tortue, un chien ou un chat.
Comment construire un objet du bon type a la volee ?
Quelle est la bonne architecture ?
Ma piste: avoir une fonction de reconstruction virtuelle dans Animal, et profiter du polymorphisme ... mais je bloque.
Marsh Posté le 13-12-2003 à 19:44:49
une grosse fonction avec un méga swith qui renvoie un pointeur Animal* vers la nouvelle bébette alouée dynamiquement.
cette fonction peut etre une fonction membre statique auquel cas elle est appelé « fabrique »
Marsh Posté le 13-12-2003 à 20:20:24
Ce serait
static Animal* Animal::fabrique(){ ?
.... mais si ce qu'on construit est, par exemple, un Chat, ca va pas etre bon vu que les Chats et les Chiens derivent d'Animal et ne sont pas encore connus ...
Marsh Posté le 13-12-2003 à 20:24:50
avec un paramètre quand même.
tu fais une fabrique dans Animal si tu connais déjà certaines sous-classes, évidemment.
Marsh Posté le 13-12-2003 à 20:35:41
Apres essai :
Code :
|
Et apres pour implementer fabrique dans Animal, comme ceci ??
Code :
|
Marsh Posté le 13-12-2003 à 20:37:11
ben non
return new Chien;
Marsh Posté le 13-12-2003 à 20:38:27
Et l'appel serait donc
Code :
|
Marsh Posté le 13-12-2003 à 20:41:58
iraysyvalo a écrit : |
Et oui, un chien est un animal. Contrairement à un animal qui n'est pas forcément un chien, capiche?
Marsh Posté le 13-12-2003 à 20:42:46
SchnapsMann a écrit : |
Marsh Posté le 13-12-2003 à 20:43:18
Taz a écrit : |
Marsh Posté le 13-12-2003 à 22:17:21
iraysyvalo a écrit : |
si animal peut attacker, alors chien le peut
Marsh Posté le 14-12-2003 à 04:55:27
Edit du code d'avant
Marsh Posté le 14-12-2003 à 08:30:00
Taz a écrit : ben là il faut caster vie un dynamic_cast. si tu utilises des propriétés personnelle à la tortue, il faut que ton objet soit une tortue et typé tel quel |
Pattern 1) Expert : celui qui a l'information s'occupe du traitement. Si tu n'as pas l'information alors ce n'est pas à toi de faire le traitement.
En l'occurence, dans cette situation on utilise un Visiteur.
Marsh Posté le 14-12-2003 à 10:22:09
Code :
|
(j'imagine que Taz corrigera ce qui lui plait pas)
voilà l'esprit de tous les services que tu veux, en version bien typée et propre.
Il y a un Pattern Fabrique Abstraite (classe dont les instances sont des usines à instances) l'intérêt est de pouvoir fabriquer des animaux "à l'aveuglette", imagine par exemple un monde un peu crado où pour avoir un animal de compagnie on doive acheter un jeton pui passer le jeton à l'Administration qui va lui fabriquer le chien et l'enregistrer légalement par la même occasion. Le jeton contiendra une référence à la Fabrique idoine, mais le fonctionnaire ne saura pas quel annimal sera créé (il s'en fout).
C'est pas top comme exemple, mais je vois pas à quoi pourrait te servir ta fabrique dans ton modèle.
Pour les traitements spécifique par animal, il y a tout le système de Visiteur, un objet qui a un traitement spécifique par animal est un VisiteurAnimalier (qui ne modélise pas une personne mais un trait de personnalité d'un objet).
Au passage, j'ai mis les fabriques en Singleton, c'est-à-dire qu'il n'existe qu'une seule instance de la classe FabriqueDeChat accessible dans la classe.
Marsh Posté le 09-12-2003 à 00:08:57
Alors une petite question surement conne mais ca coute rien de la poser...
Disons que j'ai 3 classes:
- une classe "animal" qui est la classe de base
- une classe "chat" qui hérite de "animal" et lui ajoute de nouvelles choses, etc...
- une classe "tortue" qui hérite aussi de "animal", etc...
Alors disons qu'ensuite je veux classer tout mes chats et mes tortues dans un "vector", je fais comment et est-ce possible ???
Parce que j'ai testé :
Avec des push_back() on arrive à ajouter les animaux dans la liste, par contre lorsque je veux accéder aux propriétés ou méthodes, seules celles hérités de "animal" sont disponibles...