Forum |  HardWare.fr | News | Articles | PC | S'identifier | S'inscrire | Shop Recherche
2909 connectés 

  FORUM HardWare.fr
  Programmation
  C++

  [C++ débutant] Const_cast ? :-(

 


 Mot :   Pseudo :  
 
Bas de page
Auteur Sujet :

[C++ débutant] Const_cast ? :-(

n°1306663
ParadoX
Posté le 15-02-2006 à 20:38:11  profilanswer
 

Bonjour,  
 
Tjrs dans le cadre d'un projet c++ pour la fac (Sujet), nous avons fait une Liste doublement chaînée d'objets.  
 
Nous désirons avoir une méthode de classe "print()" dans notre classe Liste. Pour effectuer ce print, on place un
itérateur sur cette liste, on le fait avancer et à chaque fois, on lui fait imprimer la valeur actuelle. Ce print
fonctionne très bien dans notre Main();

Code :
  1. //Affichage de la liste en mode texte (dans le main())
  2. void print(const Liste &uneListe)
  3. {
  4. if(!uneListe.estVide())
  5. {
  6.  int i;
  7.  Iterateur monIterateur(uneListe);
  8.  cout << "Contenu de la liste : ";
  9.  for(i = 0; i < uneListe.getNbElements(); i++)
  10.  {
  11.   cout << monIterateur.valeur().nom << " <=> ";
  12.   monIterateur.avance();
  13.  }
  14.  cout << "\n\n";
  15. }
  16. else
  17. {
  18.  cout << "La liste est Vide ! \n";
  19. }
  20. }


Maintenant, il est plus logique en conception objet d'en faire une méthode de la classe Liste. Or, nous ne parvenons
pas à passer l'itérateur sur l'instance courante de notre liste. Voici la méthode modifiée pour être une méthode de
classe:

Code :
  1. //Affichage de la liste
  2. void Liste::print() const
  3. {
  4. if(!estVide())
  5. {
  6.  int i;
  7.  Iterateur monIterateur(*this); // C'est ici que ça foire !
  8.  cout << "Contenu de la liste : ";
  9.  for(i = 0; i < getNbElements(); i++)
  10.  {
  11.   cout << monIterateur.valeur().nom << " <=> ";
  12.   monIterateur.avance();
  13.  }
  14.  cout << "\n\n";
  15. }
  16. else
  17. {
  18.  cout << "La liste est Vide ! \n";
  19. }
  20. }


 
Le compilateur gueule :
error C2664: '__thiscall Iterateur::Iterateur(class Liste & )' : cannot convert parameter 1 from 'const class Liste' to
'class Liste &'
 
Depuis quand une instance courante est-elle "const" ? Et pourquoi refuse-t-il ? Nous nous sommes rappellé d'une astuce de notre prof : Utiliser const_cast <Liste &>, mais nous n'arrivons pas à la mettre en oeuvre.  
 
Pour info, nous n'avons qu'un seul
constructeur pour l'itérateur dont voici la signature: Iterateur(Liste & );
 
Pourriez-vous nous donner un petit coup de main svp ? C'est super moche de laisser la fonction print dans le main(),
d'autant plus qu'elle tape direct dans les données membres private de notre liste, et nous avons donc du mettre la
fonction et la classe en Friend, ce qui est quand même assez moche.
 
Merci d'avance :)


Message édité par ParadoX le 15-02-2006 à 20:38:25

---------------
Pier noir la mèr - La chanson par HFR Band - Topic TrueCrypt
mood
Publicité
Posté le 15-02-2006 à 20:38:11  profilanswer
 

n°1306667
skelter
Posté le 15-02-2006 à 20:43:37  profilanswer
 

c'est simple, quand tu déclares une méthode const ca sert à quoi ?
this est en quelque sorte un parametre caché (il contient l'adresse de l'objet sur lequel s'applique la méthode), quand la méthode est const this est à consideré comme un pointeur (constant) sur objet constant
 

n°1306681
skelter
Posté le 15-02-2006 à 20:54:50  profilanswer
 

pour répondre, faudrait que ton type itérateur soit adapté à un liste constante, ca doit etre un type distinct de Iterateur avec les restrictions qu'on attent (l'interface d'un type iterateur const ne doit pas permettre de modifié la liste)

n°1306682
ParadoX
Posté le 15-02-2006 à 20:55:11  profilanswer
 

hm mais mon print doit par définition être const, non ? Que me proposes-tu comme solution à mon problème ? Je sais que This est un pointeur vers l'objet courant, mais pourquoi ma Liste actuelle est-elle const ? Ou est-ce défini ?
 
Désolé si je me répète, mais j'apprends :jap:
 
EDIT: T'as reposté avant ma réponse ^^ Je lis, et je reposte :)


Message édité par ParadoX le 15-02-2006 à 20:55:44

---------------
Pier noir la mèr - La chanson par HFR Band - Topic TrueCrypt
n°1306684
ParadoX
Posté le 15-02-2006 à 20:57:58  profilanswer
 

skelter a écrit :

pour répondre, faudrait que ton type itérateur soit adapté à un liste constante, ca doit etre un type distinct de Iterateur avec les restrictions qu'on attent (l'interface d'un type iterateur const ne doit pas permettre de modifié la liste)


 
La solution la plus simple serait donc un 2ème constructeur pour un iterateur, qui prendrait une Liste & const en paramètre si je te comprends bien ? :)


---------------
Pier noir la mèr - La chanson par HFR Band - Topic TrueCrypt
n°1306695
skelter
Posté le 15-02-2006 à 21:05:21  profilanswer
 

sans voir le code de la classe Iterateur je peux pas dire, mais je ne penses pas que modifié le constructeur suffise, en tout cas si ca marche ca peut etre un passe-droit à l'attribut de constance de ta liste, si ton type iterateur permet de modifier la liste à laquel il est lié (je sais pas comment ca marche ton truc, pourquoi pas un type membre iterateur de Liste ?) et que tu peux le construire à partir d'une liste constante ya forcement un probleme de conception
 
tu devrais faire comme la STL, des types membres iterateurs bien distinct (iterator, const_iterator, ...)


Message édité par skelter le 15-02-2006 à 21:06:08
n°1306696
ParadoX
Posté le 15-02-2006 à 21:09:04  profilanswer
 

Voici mon Iterateur:
 
.h

Code :
  1. class Iterateur
  2. {
  3. private:
  4.  Liste::Node **actuel;
  5.  Liste *liste;
  6. public:
  7.  Iterateur(Liste & );
  8.  ~Iterateur();
  9.  void avance();
  10.  void recule();
  11.  void retourTete();
  12.  Objet  valeur() const;
  13.  void ajouter(Objet, Liste& );
  14.  void supprimer();
  15.  bool iterFin() const;
  16. };


 
et le cpp:
 

Code :
  1. //Constructeur de l'iterateur
  2. Iterateur::Iterateur(Liste &maListe)
  3. {
  4. this->actuel = &(maListe.tete);
  5. this->liste = &maListe;
  6. }
  7. //Destructeur
  8. Iterateur::~Iterateur()
  9. {
  10. //rien à faire
  11. }
  12. //Méthodes
  13. //Retour de la valeur contenue dans le node actuelle
  14. Objet Iterateur::valeur() const
  15. {
  16. return (**actuel).valeur;
  17. }
  18. //Fait avancer l'iterateur
  19. void Iterateur::avance()
  20. {
  21. this->actuel = &((*(*actuel)).suivant);
  22. }
  23. //Fait reculer l'iterateur
  24. void Iterateur::recule()
  25. {
  26. this->actuel = &((*(*actuel)).precedent);
  27. }
  28. //Ajoute un element dans la liste
  29. void Iterateur::ajouter(Objet maValeur, Liste &uneListe)
  30. {
  31. //Creation d'un nouveau noeud, et remplissage de celui-ci
  32. Liste::Node *nouv = new Liste::Node();
  33. nouv->valeur = maValeur;
  34. //2 cas: La liste est vide, ou elle ne l'est pas
  35. if(!uneListe.estVide())
  36. {
  37.  nouv->suivant = (*(*actuel)).suivant;
  38.  nouv->precedent = (*actuel);
  39.  ((*(*actuel)).suivant)->precedent = nouv;
  40.  (*(*actuel)).suivant = nouv;
  41. }
  42. else
  43. {
  44.  nouv->suivant = NULL;
  45.  nouv->precedent = NULL;
  46.  uneListe.tete = nouv;
  47.  uneListe.queue = nouv;
  48. }
  49. uneListe.incNbElements();
  50. }


 
Il faudrait que je fasse plusieurs types d'iterateurs, un pour lire, un pour écrire ? (an héritant la classe iterateur 2 fois, par ex ?)
 
Merci de ton aide :)
 
 


---------------
Pier noir la mèr - La chanson par HFR Band - Topic TrueCrypt
n°1306698
skelter
Posté le 15-02-2006 à 21:13:36  profilanswer
 

en partant de ca (parce que en fait faudrais tout reconcevoir mais tu n'as sans doute pas le temps), le mieux (je penses) c'est de faire comme tu dis, un type iterateur_base a partir duquel tu fais derivé iterateur_const et iterateur

n°1306702
ParadoX
Posté le 15-02-2006 à 21:21:53  profilanswer
 

Ok :)
 
Si j'avais eu le temps, qu'aurais-tu proposé ? Si on se bouge un peu (on est en binomes), pourquoi pas ... Le prof a bien insisté sur le "orienté objet" ! Alors si on peut faire mieux, ou du moins essayer ... :)


---------------
Pier noir la mèr - La chanson par HFR Band - Topic TrueCrypt
n°1306706
skelter
Posté le 15-02-2006 à 21:27:29  profilanswer
 

faire comme la STL
 
 

Code :
  1. class list
  2. {
  3. public:
  4. // types membres public
  5. struct iterator { ... };
  6. struct const_iterator { ... };
  7. // methode pour obtenir un iterateurs
  8. const_iterator begin() const;
  9. iterator begin();
  10. const_iterator end() const;
  11. iterator end();
  12. ...
  13. };

mood
Publicité
Posté le 15-02-2006 à 21:27:29  profilanswer
 

n°1306708
ParadoX
Posté le 15-02-2006 à 21:31:14  profilanswer
 

Je ne connais pas la STL, et je ne vois pas trop ou tu veux en venir ... au lieu de faire une classe Iterator, tu en fais des structs internes à la classe Liste ?
 
Au pire des cas, je vais déjà tenter comme tu m'as dit plus haut, on verra bine pour le reste .. merci en tout cas :)


---------------
Pier noir la mèr - La chanson par HFR Band - Topic TrueCrypt
n°1306709
skelter
Posté le 15-02-2006 à 21:37:16  profilanswer
 

oui ca chanse pas grands choses, dans les deux cas faut avoir 2 types distincts, c'est au niveau de la conception que c'est différent car avec la stl c'est le conteneur qui construit les iterateurs et non l'appelant
 
la STL = Standard Template Library (en fait ca fais partie de la SL = Standard Library)
 
http://fr.wikipedia.org/wiki/Standard_Template_Library


Message édité par skelter le 15-02-2006 à 21:37:33

Aller à :
Ajouter une réponse
  FORUM HardWare.fr
  Programmation
  C++

  [C++ débutant] Const_cast ? :-(

 

Sujets relatifs
[Débutant] Socket[C++ débutant] Liste chaînée, suite des problemes :D
ptit'pb à résoudre, débutant total[resolu]Debutant en php - derniere connection
(question débutant) Afficher du texte à partir d'un .txtDébutant en POO, class mysql php5
[JAVA - Débutant] - Probleme premier programme en JAVAstructure if - else (débutant)
Débutant...clé sympa du registre (debutant)
Plus de sujets relatifs à : [C++ débutant] Const_cast ? :-(


Copyright © 1997-2022 Hardware.fr SARL (Signaler un contenu illicite / Données personnelles) / Groupe LDLC / Shop HFR