[C++] Template & Liste chaîné

Template & Liste chaîné [C++] - C++ - Programmation

Marsh Posté le 18-06-2005 à 10:38:08    

Hello, je suis en train de coder une template de liste chaînée. Celle ci va contenir des objets divers.
Mais je n'y arrive pas. J'ai beucoup de souci de compilation au niveau de mes malloc. Pouvez vous m'aider??  
Voivi ma classe :

Code :
  1. #ifndef LISTE_H
  2. #define LISTE_H
  3. #include <string.h>
  4. #include <stdlib.h>
  5. #include <stdio.h>
  6. #include <iostream.h>
  7. template <class T>
  8. class Liste
  9. {
  10.    typedef struct listeC
  11.     {
  12.       T _element ;
  13.       struct liste *precedent ;
  14.       struct liste *suivant ;
  15.     }liste; 
  16.    liste *debut ; 
  17.    int nbElement ;
  18. public:
  19.    Liste() ;
  20.    Liste( const T &element ) ;
  21.    int ajouteElement( const T &element ) ;
  22.    int getNbElement() ;
  23. };
  24. template <class T>
  25. Liste<T>::Liste()
  26. {
  27.    debut = NULL ;
  28.    nbElement = 0 ;
  29. }
  30. template <class T>
  31. Liste<T>::Liste( const T &element )
  32. {
  33.    debut = ( struct liste * ) malloc( sizeof( T ) );
  34.    _element = element ;
  35.    debut.precedent = NULL ;
  36.    debut.suivant = NULL ;
  37.    nbElement = 1;
  38. }
  39. template <class T>
  40. int Liste<T>::ajouteElement( const T &element )
  41. {
  42.    liste *courant ;
  43.  
  44.    if( debut == NULL )
  45.    {
  46.       debut = ( struct liste * ) malloc( sizeof( T ) );
  47.       _element = element ;
  48.       nbElement = 1;
  49.    }
  50.    else
  51.    {
  52.       while( courant->suivant != debut )
  53.       {
  54.          courant = courant->suivant ;
  55.       }
  56.       if( courant->suivant == debut )
  57.       {
  58.          courant->suivant = ( struct liste * ) malloc( sizeof( T ) );
  59.          courant->suivant->_element = element;
  60.          courant->suivant->suivant = debut;
  61.       }
  62.    }
  63.    return 1;
  64. }
  65. template <class T>
  66. int Liste<T>::getNbElement()
  67. {
  68.    return nbElement;
  69. }
  70. #endif


 
Dans ma classe pour l'instant j'ai donc fait :
 
 
      un conctructeur
      un conctructeur de recopie
      une méthode permettant d'ajouter une élément dans ma liste chaîné
      un accesseur qui retourne le nombre d'élément de ma liste chaîné
 
 
 
J'ai en attribut de classe une structure : ma liste chainé
l'adresse du début de ma liste chainé
et un entier qui correspond au nombre d'élément de ma liste chainé.
Ma liste chainé est une liste doublement chainé avec un lien vers le chainon suivant et un lien vers le chainon précédent.
C'est donc une liste chainé circulaire.
 
Cette ligne de code pose problème par exemple :

Code :
  1. debut = ( struct liste * ) malloc( sizeof( T ) );


Je ne sais pas quoi mettre dans le malloc et dans le typage :
struct liste * ou T?
struct liste * parait le plus évident. Mais je dois surement fournir aussi le type de liste? enfin je veux dire le type de l'élément de ma liste non?
C'est un peu compliqué...
Aidez moi s'il vous plait  :pfff:

Reply

Marsh Posté le 18-06-2005 à 10:38:08   

Reply

Marsh Posté le 18-06-2005 à 10:51:31    

qu'est ce que tu fous avec des malloc ? t'es en C++, les malloc n'ont rien à faire ici !


---------------
J'ai un string dans l'array (Paris Hilton)
Reply

Marsh Posté le 18-06-2005 à 10:53:27    

Je fais un new alors??

Code :
  1. debut = new struct liste ( T );


Comme ca?

Reply

Marsh Posté le 18-06-2005 à 10:54:05    

voila


---------------
J'ai un string dans l'array (Paris Hilton)
Reply

Marsh Posté le 18-06-2005 à 10:55:44    

En C++, on utilise new: debut = new T;
 
Rassure-moi, c'est juste à titre d'exercice que tu crées cette classe ? Tu n'as pas l'intention de l'utiliser par la suite ?


Message édité par el muchacho le 18-06-2005 à 11:03:26
Reply

Marsh Posté le 18-06-2005 à 10:58:50    

Oui oui c'est un projet débile de fin d'année. je suis obligé d'utiliser ce que j'ai vu pendant l'année. Je mélange donc C et C++... C'est un petit projet.

Reply

Marsh Posté le 18-06-2005 à 11:01:45    

Mon code devien donc :

Code :
  1. #ifndef LISTE_H
  2. #define LISTE_H
  3. #include <string.h>
  4. #include <stdlib.h>
  5. #include <stdio.h>
  6. #include <iostream.h>
  7. template <class T>
  8. class Liste
  9. {
  10. typedef struct listeC
  11.     {
  12.  T _element ;
  13.  struct liste *precedent ;
  14.  struct liste *suivant ;
  15.     }liste;
  16. liste *debut ;
  17. int nbElement ;
  18. public:
  19. Liste() ;
  20. Liste( const T &element ) ;
  21. int ajouteElement( const T &element ) ;
  22. int getNbElement() ;
  23. };
  24. template <class T>
  25. Liste<T>::Liste()
  26. {
  27. debut = NULL ;
  28. nbElement = 0 ;
  29. }
  30. template <class T>
  31. Liste<T>::Liste( const T &element )
  32. {
  33. debut = new T;
  34. _element = element ;
  35. debut.precedent = NULL ;
  36. debut.suivant = NULL ;
  37. nbElement = 1;
  38. }
  39. template <class T>
  40. int Liste<T>::ajouteElement( const T &element )
  41. {
  42. liste *courant ;
  43. if( debut == NULL )
  44. {
  45.  debut = new T;
  46.  _element = element ;
  47.  nbElement = 1;
  48. }
  49. else
  50. {
  51.  while( courant->suivant != debut )
  52.  {
  53.   courant = courant->suivant ;
  54.  }
  55.  if( courant->suivant == debut )
  56.  {
  57.   courant->suivant = new T;
  58.   courant->suivant->_element = element;
  59.   courant->suivant->suivant = debut;
  60.   debut->precedent = courant->suivant;
  61.  }
  62. }
  63. return 1;
  64. }
  65. template <class T>
  66. int Liste<T>::getNbElement()
  67. {
  68. return nbElement;
  69. }
  70. #endif


 

Reply

Marsh Posté le 18-06-2005 à 11:02:52    

Tu mélanges tellement que tu t'y perds, et nous avec... Ca fait 3 fois que j'édite mon post pour la bonne syntaxe du new...

Reply

Marsh Posté le 18-06-2005 à 11:03:22    

ah oui, liste est un template, j'avais pas fait gaffe. c'est donc bien liste <T> et pas liste (T). mais de toute façon, comme muchacho et moi te l'avons dit, en C++ les allocations se font avec new


---------------
J'ai un string dans l'array (Paris Hilton)
Reply

Marsh Posté le 18-06-2005 à 11:06:22    

Mais c'est une nouvelle liste de type T. Et non pas un nouvel objet de type T.
Donc ca ne devrait pas être comme ceci plutôt:

Code :
  1. debut = new Liste<T>;

Reply

Marsh Posté le 18-06-2005 à 11:06:22   

Reply

Marsh Posté le 18-06-2005 à 11:09:41    

En fait, sans compilo pour essayer, je dirais qu'il faut que liste soit une classe avec un constructeur que tu initialises en appelant le new:
liste<T> *debut = new liste(T, prec, suiv);
 
Là, tu mélanges debut : premier élément de la liste et le type objet T.  
ton malloc était faux : c'était sizeof(struct listeC) et non sizeof(T).
D'où la confusion que tout le monde a faite.


Message édité par el muchacho le 18-06-2005 à 11:11:42
Reply

Marsh Posté le 18-06-2005 à 11:11:26    

non c'est new T : tu ajoutes un élément à ta liste, pas une liste !
 
edit: ptain, je m'y perds les pinceaux à son truc :pt1cable:


Message édité par Harkonnen le 18-06-2005 à 11:12:18

---------------
J'ai un string dans l'array (Paris Hilton)
Reply

Marsh Posté le 18-06-2005 à 11:11:46    

C'est ca en fait le gros problème.
Comment initialisé mon debut?
debut est un pointeur sur une structure :

Code :
  1. typedef struct listeC
  2.      {
  3.          T _element ;
  4.          struct liste *precedent ;
  5.          struct liste *suivant ;
  6.      }liste;


la structure peut contenir un objet de type T.
Donc quand j'initialise debut je dois faire ceci :
debut = new liste;
Mais il faut focément que je précise le type que ma liste va contenir (T donc).
Comment faire ca?
debut = new liste<T>; ??

Reply

Marsh Posté le 18-06-2005 à 11:12:24    

Harko > Non. Lis mon post.


Message édité par el muchacho le 18-06-2005 à 11:13:09
Reply

Marsh Posté le 18-06-2005 à 11:15:09    

Spir a écrit :

C'est ca en fait le gros problème.
Comment initialisé mon debut?
debut est un pointeur sur une structure :

Code :
  1. typedef struct listeC
  2.      {
  3.          T _element ;
  4.          struct liste *precedent ;
  5.          struct liste *suivant ;
  6.      }liste;


la structure peut contenir un objet de type T.
Donc quand j'initialise debut je dois faire ceci :
debut = new liste;
Mais il faut focément que je précise le type que ma liste va contenir (T donc).
Comment faire ca?
debut = new liste<T>; ??


 
liste<T> *debut = new liste(T, 0, 0);
 
cf mon post précédent


Message édité par el muchacho le 18-06-2005 à 11:17:10
Reply

Marsh Posté le 18-06-2005 à 11:18:08    

Ouais mais il y a confusion entr le nom de la classe et le nom de la structure.
Ma classe s'appel Liste la structure liste.
debut est un attribut de la classe Liste.
C'est un pointent sur une structure liste.
Donc si je fais ce que tu dis :

Code :
  1. liste<T> *debut = new liste(T, prec, suiv);


ca fais spé... liste est une structure pas une classe?!

Reply

Marsh Posté le 18-06-2005 à 11:19:31    

je veux dire si je fais :

Code :
  1. liste<T> *debut = new liste(T, prec, suiv);


Je dois créé un constructeur de liste??? je ne capte pas.

Reply

Marsh Posté le 18-06-2005 à 11:19:51    

Ben t'en fais une classe, et tu renommes ListeC en Element, et comme ça, on arrête de tout mélanger. Parce qu'au fonds, ce que tu appelles liste * n'est qu'un élément de l'objet Liste.


Message édité par el muchacho le 18-06-2005 à 11:20:55
Reply

Marsh Posté le 18-06-2005 à 11:21:16    

C'est ps compliqué ce que je veux faire. je veux juste faire un classe template qui manipule une liste chainé.
J'ai donc en attribut la déclaration de la structure de ma liste chainé, et un pointeur debut qui pointe sur l'adresse du début de ma liste chainé.

Reply

Marsh Posté le 18-06-2005 à 11:22:11    

Ben oui mais tu mélanges tout parce que tu raisonnes à la C.

Reply

Marsh Posté le 18-06-2005 à 11:22:30    

Ok donc je fais un classe template ListeC qui décrit une liste chainé.
Et après je fais une classe Liste qui manipule ma liste chainé template.

Reply

Marsh Posté le 18-06-2005 à 11:24:25    

J'ai trouvé quelque chose sur le net qui ressemble à ce que je veux faire :
liste.h :

Code :
  1. #ifndef _LISTE
  2. #define _LISTE
  3. #include <stdio.h>
  4. template <class T>
  5. class Cellule
  6. {
  7. public:
  8. T valeur;
  9. Cellule *suivant;
  10. Cellule();
  11. Cellule(T);
  12. // ~Cellule();
  13. T recValeur();
  14. Cellule<T> *recSuivant();
  15. affSuivant(Cellule<T> *);
  16. supprSuivant();
  17. };
  18. template <class T>
  19. class Liste
  20. {
  21. public:
  22. Cellule<T> *debut;
  23. Liste();
  24. Liste(T);
  25. // ~Liste();
  26. int recNbElements();
  27. T *recElement(int);
  28. inserer(int, T);
  29. int *rechercher(T);
  30. supprimer(int);
  31. // int afficher();
  32. };
  33. #endif


 
 
liste.cpp

Code :
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <iostream.h>
  4. #include <string.h>
  5. #include "liste.h"
  6. template <class T>
  7. Cellule<T>::Cellule()
  8. {
  9. suivant=NULL;
  10. }
  11. template <class T>
  12. Cellule<T>::Cellule(T v)
  13. {
  14. valeur=v;
  15. suivant=NULL;
  16. }
  17. /*
  18. template <class T>
  19. Cellule<T>::~Cellule()
  20. {
  21. if(suivant!=NULL)
  22.  suivant->~Cellule();
  23. free(suivant);
  24. }
  25. */
  26. template <class T>
  27. T Cellule<T>::recValeur()
  28. {
  29. return(valeur);
  30. }
  31. template <class T>
  32. Cellule<T> *Cellule<T>::recSuivant()
  33. {
  34. return(suivant);
  35. }
  36. template <class T>
  37. Cellule<T>::affSuivant(Cellule<T> *s)
  38. {
  39. if(s==NULL)
  40.  suivant=NULL;
  41. else
  42. {
  43.  suivant=new Cellule;
  44.  *suivant=*s;
  45. }
  46. }
  47. template <class T>
  48. Cellule<T>::supprSuivant()
  49. {
  50. suivant->~Cellule();
  51. free(suivant);
  52. }
  53. template <class T>
  54. Liste<T>::Liste()
  55. {
  56. debut=NULL;
  57. }
  58. template <class T>
  59. Liste<T>::Liste(T v)
  60. {
  61. debut=new Cellule(v);
  62. }
  63. /*
  64. template <class T>
  65. Liste<T>::~Liste()
  66. {
  67. if(debut!=NULL)
  68.  debut->~Cellule();
  69. free(debut);
  70. }
  71. */
  72. template <class T>
  73. int Liste<T>::recNbElements()
  74. {
  75. int n;
  76. Cellule<T> *pc;
  77. n=0;
  78. pc=debut;
  79. while(pc!=NULL)
  80. {
  81.  pc=pc->recSuivant();
  82.  n++;
  83. }
  84. return(n);
  85. }
  86. template <class T>
  87. T *Liste<T>::recElement(int p)
  88. {
  89. int i;
  90. Cellule<T> *pc;
  91. T *e;
  92. i=1;
  93. pc=debut;
  94. e=NULL;
  95. if(p>0)
  96. {
  97.  while(pc!=NULL && i<p)
  98.  {
  99.   pc=pc->recSuivant();
  100.   i++;
  101.  }
  102.  if(pc!=NULL)
  103.  {
  104.   e=new T;
  105.   *e=pc->recValeur();
  106.  }
  107. }
  108. return(e);
  109. }
  110. template <class T>
  111. Liste<T>::inserer(int p ,T v)
  112. {
  113. int i;
  114. Cellule<T> c(v), *pc;
  115. if(p==1)
  116. {
  117.  if(recNbElements()!=0)
  118.   c.affSuivant(debut);
  119.  debut=new Cellule<T>;
  120.  *debut=c;
  121. }
  122. else if(p>1)
  123. {
  124.  i=1;
  125.  pc=debut;
  126.  while(pc->recSuivant()!=NULL && i<p-1)
  127.  {
  128.   pc=pc->recSuivant();
  129.   i++;
  130.  }
  131.   c.affSuivant(pc->recSuivant());
  132.  pc->affSuivant(&c);
  133. }
  134. }
  135. template <class T>
  136. int *Liste<T>::rechercher(T e)
  137. {
  138. int *pos, n, i;
  139. pos=NULL;
  140. i=1;
  141. n=recNbElements();
  142. while(pos==NULL && i<=n)
  143. {
  144.  if(*recElement(i)==e)
  145.  {
  146.   pos=new int;
  147.   *pos=i;
  148.  }
  149.  i++;
  150. }
  151. return(pos);
  152. }
  153. template <class T>
  154. Liste<T>::supprimer(int p)
  155. {
  156. int i;
  157. Cellule<T> *pc, *tampon
  158. if(p==1)
  159.  debut=debut->recSuivant();
  160. else if(i>1)
  161. {
  162.  i=1;
  163.  pc=debut;
  164.  while(pc->recSuivant()!=NULL && i<p-1)
  165.  {
  166.   pc=pc->recSuivant();
  167.   i++;
  168.  }
  169.  if(pc->recSuivant()!=NULL)
  170.  {
  171.   tampon=pc->recSuivant();
  172.   pc->affSuivant(tampon->recSuivant());
  173.   tampon->~Cellule();
  174.  }
  175. }
  176. }
  177. /*template <class T>
  178. int Liste::afficher()
  179. */

Reply

Marsh Posté le 18-06-2005 à 11:26:08    

Déjà, fais-en une version non template qui marche...
 
 - une classe Liste qui est celle que tu as définie
 - une classe Element de la liste qui sera une sorte de wrapper du type T, définie comme ta struct ListeC, et qui n'a besoin comme méthodes qu'un constructeur et un destructeur.


Message édité par el muchacho le 18-06-2005 à 11:27:52
Reply

Marsh Posté le 18-06-2005 à 11:27:24    

Spir a écrit :

J'ai trouvé quelque chose sur le net qui ressemble à ce que je veux faire :
liste.h :

Code :



 
C'est très exactement ce que je viens de te décrire: ici Cellule est ma classe Element.

Reply

Marsh Posté le 18-06-2005 à 11:28:27    

Voilà bon bah je vais essayer de faire ca. Un classe qui décrit ma liste chainé.
Et une classe qui exploite cette liste chainé.

Reply

Marsh Posté le 27-06-2005 à 18:45:59    

Juste unt truc :

el muchacho a écrit :

Rassure-moi, c'est juste à titre d'exercice que tu crées cette classe ? Tu n'as pas l'intention de l'utiliser par la suite ?


 
Pourquoi ? C'est mal ?

Reply

Marsh Posté le 27-06-2005 à 18:48:07    

En un mot, oui. Y'a une lib standard qui fait ça très bien, et probablement mieux que tout ce que vous pourrez pondre, alors autant l'utiliser.


Message édité par el muchacho le 27-06-2005 à 18:49:08
Reply

Marsh Posté le 27-06-2005 à 18:50:04    

aukey

Reply

Marsh Posté le    

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed