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

  FORUM HardWare.fr
  Programmation
  C++

  Spécialisation des templates

 


 Mot :   Pseudo :  
 
 Page :   1  2
Page Précédente
Auteur Sujet :

Spécialisation des templates

n°470329
Taz
bisounours-codeur
Posté le 28-07-2003 à 23:31:46  profilanswer
 

l'intéret c'est d'avoir une version générique passe partout, et des versions spécialisées pour certains types, souvent pour permettre des optimisations.
 
par exemple std::swap est muni de spécialisation pour les types de la STL. par exemple: quand on veut permuter 2 std::vector, il serait bête de procéder à plusieurs recopies (c'est à dire le swap de base, avec un variable temporaire) alors qu'on pourrait seulement se contenter de permuter 2 pointeurs (on permute les implémentations)
 
le code parle de lui même, petit exemple clef en main
 

Code :
  1. #include <iostream>
  2. #include <typeinfo>
  3. using namespace std;
  4. class Bar{};
  5. template<class T>
  6. class Foo
  7. {
  8.   T item;
  9. public:
  10.   static void say_hello()
  11.   {
  12.     cout << "Foo " << typeid(T).name() << " générique" << endl;
  13.   }
  14. };
  15. // spécialisation pour un type donné
  16. template<>
  17. class Foo<Bar>
  18. {
  19. public:
  20.   static void say_hello()
  21.   {
  22.     cout << "FooBar" << endl;
  23.   }
  24. };
  25. // spécialisation partielle pour tout type de pointeur
  26. template<class T>
  27. class Foo< T* >
  28. {
  29.   T *item;
  30. public:
  31.   static void say_hello()
  32.   {
  33.     cout << "Foo " << typeid(T).name() << " spécialisé pointeur" << endl;
  34.   }
  35. };
  36. // spécialisation pour les pointeurs de void
  37. template <>
  38. class Foo<void*>
  39. {
  40.   void *item;
  41. public:
  42.   static void say_hello()
  43.   {
  44.     cout << "Foo " << typeid(void).name() << " spécialisé pointeur" << endl;
  45.   }
  46. };
  47. int main()
  48. {
  49.   Foo<int>::say_hello();
  50.   Foo<Bar>::say_hello();
  51.   Foo<bool*>::say_hello();
  52.   Foo<void*>::say_hello();
  53. }


 
 
autre exemple
 

Code :
  1. template<unsigned Dim, typename T>
  2. struct Dot;
  3. template<typename T>
  4. struct Dot<1, T>
  5. {
  6.   static inline T dot(const T *a, const T *b)
  7.   {
  8.     return *a * *b;
  9.   }
  10. };
  11. template<unsigned Dim, typename T>
  12. struct Dot
  13. {
  14.   static inline T dot(const T *a, const T *b)
  15.   {
  16.     return (*a * *b) + Dot<Dim-1, T>::dot(a+1, b+1);
  17.   }
  18. };
  19. template<unsigned Dim, typename T>
  20. inline T dot(const T *a, const T *b)
  21. {
  22.   return Dot<Dim, T>::dot(a, b);
  23. }


 
 
et encore un
 

Code :
  1. template<unsigned m, unsigned n>
  2. struct Ackermann;
  3. template<unsigned n>
  4. struct Ackermann<0, n>
  5. {
  6.   static const unsigned value = n+1;
  7. };
  8. template<unsigned m>
  9. struct Ackermann<m, 0>
  10. {
  11.   static const unsigned value = Ackermann<m-1, 1>::value;
  12. };
  13. template<unsigned m, unsigned n>
  14. struct Ackermann
  15. {
  16.   static const unsigned value = Ackermann<m-1, Ackermann<m, n-1>::value >::value;
  17. };
  18. #include <iostream>
  19. using namespace std;
  20. int main()
  21. {
  22.   cout << Ackermann<3, 4>::value << endl;
  23. }


Message édité par Taz le 05-10-2003 à 14:53:29
mood
Publicité
Posté le 28-07-2003 à 23:31:46  profilanswer
 

n°509133
blackgodde​ss
vive le troll !
Posté le 06-09-2003 à 01:24:00  profilanswer
 

ah, c interressant, je vais travailler ca, merci :)


---------------
-( BlackGoddess )-
n°531806
Evadream -​jbd-
Posté le 05-10-2003 à 13:48:39  profilanswer
 

Bonjour tout le monde !
 
J'ai hésite à créer un nouveau topic pour ma question. Taz, si tu penses que ca n'a pas sa place ici vu que je débute avec cà, je créerai un topic.
 
Ma question porte sur la spécialisation partielle des fonctions membres. Par exemple, voici un début de classe Matrix :
 
 

Code :
  1. template<class T, unsigned short i_row, unsigned short i_column>
  2. class CMatrix {    /* Ligne 18 */
  3. public:
  4.  CMatrix() ;
  5.  ~CMatrix() ;
  6.  void fill(const T=0) ;
  7.  void show() const ;
  8.                 T computedet() const ;
  9.  inline bool isSquare() { return (row==column) ; }
  10. private:
  11.  valarray<T> elements; 
  12.  unsigned short row ;
  13.  unsigned short column ;
  14.                 T det ;
  15. };


 
 
Mon but est ici de créer une classe permettant de manipuler des matrices d'un type T, de taille i_row * i_column.
 
J'aimerais pouvoir spécialiser quelques fonctions membres suivant le couple i_row et i_column, pour par exemple la fonction de calcul du déterminant.
 
 
D'abord, je définis une fonction générique :
 

Code :
  1. template<class T, unsigned short i_row, unsigned short i_column>
  2. T CMatrix<T, i_row, i_column>::computedet() const {
  3. // ...
  4. }


 
Je souhaiterais pouvoir spécialiser le calcul de déterminant pour  des valeurs particulières de i_row et i_column, par exemple 2. J'ai essayé cà :
 

Code :
  1. template<class T>
  2. T CMatrix<T, 2, 2>::computedet() const {   /* Ligne 80 */
  3. // ...
  4. }


 
Mais le compilateur me fait comprendre bien gentiment que c'est pas bon :
 


CMatrix.h:80: invalid use of undefined type `class CMatrix<T, 2, 2>'
CMatrix.h:18: declaration of `class CMatrix<T, 2, 2>'
CMatrix.h:80: template definition of non-template `T CMatrix<T, 2, 2>::computedet() const'


 
 
Je m'en suis sorti un temps à l'aide du polymorphisme et de l'héritage en changeant de point de vue, mais j'aimerais comprendre ici pourquoi ca ne fonctionne pas, mon but étant avant tout d'apprendre à manipuler les template :)
 
Merci à vous !


Message édité par Evadream -jbd- le 05-10-2003 à 13:51:26
n°531825
Taz
bisounours-codeur
Posté le 05-10-2003 à 14:49:31  profilanswer
 

je lis à l'instant ta question : je te trouverais la référence, mais la spécialisation partielle de fonction n'est pas possible, donc idem pour les fonctions membres


Message édité par Taz le 10-02-2004 à 10:43:03
n°531829
Evadream -​jbd-
Posté le 05-10-2003 à 14:58:13  profilanswer
 

Ok, au moins la réponse a le mérite d'être courte. De toute facon il me semblait plus cohérent d'utiliser le polymorphisme et l'héritage pour arriver à mes fins dans ce problème précis.
 
Je suis très intéressé par la référence, si tu tombes dessus :)
 
Encore merci à toi pour ta réponse !

n°531831
Taz
bisounours-codeur
Posté le 05-10-2003 à 15:00:59  profilanswer
 

non, reste avec les templates. seulement, défni une classe d'aide, avec une unique fonction membre static que tu spécialises autant que tu veux

n°531833
Taz
bisounours-codeur
Posté le 05-10-2003 à 15:02:32  profilanswer
 

la référence dans cet autre sujet (vers la fin) http://forum.hardware.fr/forum2.ph [...] 218&cat=10

n°531839
Evadream -​jbd-
Posté le 05-10-2003 à 15:07:42  profilanswer
 

Taz a écrit :

non, reste avec les templates. seulement, défni une classe d'aide, avec une unique fonction membre static que tu spécialises autant que tu veux


 
Ok je vais voir dans cette direction ! Et merci pour la référence !
 
@+

n°531842
schnapsman​n
Zaford Beeblefect
Posté le 05-10-2003 à 15:14:59  profilanswer
 

Evadream -jbd- a écrit :


 
Ok je vais voir dans cette direction ! Et merci pour la référence !
 
@+


 
ou alors tu spécialise toute la classe (template<class T> class CMatrix<T,2,2> ), à toi de voir.


---------------
From now on, you will speak only when spoken to, and the first and last words out of your filthy sewers will be "Sir!"
n°531870
Evadream -​jbd-
Posté le 05-10-2003 à 15:59:41  profilanswer
 

Mmm pourquoi pas, mais ca me semble être une solution de "facilité", non ? Enfin j'ai pas trop de recul vis à vis de ces problèmes, je vais explorer les deux voies :)
 
Merci à toi pour la proposition !


Message édité par Evadream -jbd- le 05-10-2003 à 16:05:57
mood
Publicité
Posté le 05-10-2003 à 15:59:41  profilanswer
 

n°531872
Taz
bisounours-codeur
Posté le 05-10-2003 à 16:13:14  profilanswer
 

ce n'est pas une solution de facilité, c'est une très bonne solution. d'ailleurs ça me fait penser à un truc ...

n°531874
Evadream -​jbd-
Posté le 05-10-2003 à 16:15:46  profilanswer
 

Taz > Je vais utiliser la solution de SchnapsMann mais je garde ta solution sous la main. Je me laisse un peu de temps pour la mettre en place, si j'ai des soucis, je te demanderais :)
 
Merci encore !

n°531875
Evadream -​jbd-
Posté le 05-10-2003 à 16:17:20  profilanswer
 

Taz a écrit :

ce n'est pas une solution de facilité


 
Toutes mes confuses, il faut que j'arrête d'écrire tout ce que je pense =)

n°531877
Taz
bisounours-codeur
Posté le 05-10-2003 à 16:20:11  profilanswer
 

tant pis pour toi je t'aurais prévenu ... tu vas devoir te cogner toute la définition de la classe ...

n°531878
Evadream -​jbd-
Posté le 05-10-2003 à 16:21:51  profilanswer
 

Question : la spécialisation de la classe toute entière m'oblige t'elle à réecrire toutes les fonctions membres du modèle ?

n°531880
Evadream -​jbd-
Posté le 05-10-2003 à 16:22:30  profilanswer
 

Excellent, cross posting. Bon je laisse ma réponse pour la postérité.

n°531907
Evadream -​jbd-
Posté le 05-10-2003 à 17:31:18  profilanswer
 

J'ai du mal :|
 
J'ai essayé de procéder de la sorte, ds ma class CMatrix, est-ce correct ?
 

Code :
  1. template<class T, unsigned short i_row, unsigned short i_column>
  2. class CMatrix {
  3. // ...
  4. template<unsigned short a, unsigned short b>
  5. static void computedet() ;
  6. // ...


 
Par exemple, je veux spécialiser cette fonction pour les matrices 2,2, comment dois m'y prendre ? :
 

Code :
  1. template<class T, unsigned short i_row, unsigned short i_column>
  2. template<>
  3. T CMatrix<T, i_row, i_column>::computedet<2,2>() {
  4. // ...
  5. }


 
 

seulement, défini une classe d'aide, avec une unique fonction membre static que tu spécialises autant que tu veux


 
Je ne vois pas comment faire :/ Comment produire une fonction générique, et des fonctions spécialisées en utilisant ce mécanisme ?
 
Désolé de pas comprendre au quart de tour, malgré la qualité de tes topics.


Message édité par Evadream -jbd- le 05-10-2003 à 17:34:20
n°531927
Taz
bisounours-codeur
Posté le 05-10-2003 à 18:02:35  profilanswer
 

ça t'arrive de lire ?

Citation :

la spécialisation partielle de fonction n'est pas possible

[:quoted]

n°531930
Taz
bisounours-codeur
Posté le 05-10-2003 à 18:04:07  profilanswer
 

car c'est une sorte de spécialisation. ça va pouvoir marcher, mais tu vas dupliquer trop de code.
donc fais une classe extérieure pour calculer les det
 

n°531935
Evadream -​jbd-
Posté le 05-10-2003 à 18:07:09  profilanswer
 

Taz a écrit :

non, reste avec les templates. seulement, défni une classe d'aide, avec une unique fonction membre static que tu spécialises autant que tu veux


 
Je pensais que tu me proposais ici une solution pour pouvoir retrouver un mécanisme de spécialisation partiel pour des fonctions membres.
 
Lorsque j'ai utilisé la solution de SchnapsMann, tu as laissé entendre qu'il existait une meilleure solution  
 


tant pis pour toi je t'aurais prévenu ... tu vas devoir te cogner toute la définition de la classe ...

 
 
C'est cà que j'essaye en vain de réaliser, c'est tout :/
 

n°531937
Evadream -​jbd-
Posté le 05-10-2003 à 18:08:29  profilanswer
 

Taz a écrit :


donc fais une classe extérieure pour calculer les det


 
Ok ! Merci !

n°531939
Taz
bisounours-codeur
Posté le 05-10-2003 à 18:09:56  profilanswer
 

Evadream -jbd- a écrit :


 
Je pensais que tu me proposais ici une solution pour pouvoir retrouver un mécanisme de spécialisation partiel pour des fonctions membres.

c'est le cas. une classe avec une seule fonction statique entièrement dédiée au calcul d'une fonction. tu peux la spécialiser dans tous les sens, tu réécris tout le code à chaque fois, ce qui n'est pas plus volumineux qu'une hypotétique spécialisation partielle de fonctions

n°531969
Evadream -​jbd-
Posté le 05-10-2003 à 19:08:07  profilanswer
 

/me n'avait remarqué que tu avais édité ton premier post pour y ajouter des exemples ! Merci !

n°636430
blackgodde​ss
vive le troll !
Posté le 09-02-2004 à 20:20:49  profilanswer
 

il est possible de spécialiser un destructeur virtuel ?
 
(je remonte un vieux topic, mais il me semble que ce soit la place de la question :p)
 
j'ai essayer de faire ca :
 

Code :
  1. template<typename T>
  2. class list
  3. {
  4.   // ...
  5.  
  6.   virtual ~list()
  7.   {
  8.   }
  9. };
  10. // spéclialisation pointeur
  11. template<typename T>
  12. virtual list<T*>::~list()
  13. {
  14. }


 
mais ca compile pas ...


---------------
-( BlackGoddess )-
n°636436
Kristoph
Posté le 09-02-2004 à 20:31:13  profilanswer
 

BlackGoddess a écrit :

il est possible de spécialiser un destructeur virtuel ?
 
(je remonte un vieux topic, mais il me semble que ce soit la place de la question :p)
 
j'ai essayer de faire ca :
 

Code :
  1. template<typename T>
  2. class list
  3. {
  4.   // ...
  5.  
  6.   virtual ~list()
  7.   {
  8.   }
  9. };
  10. // spéclialisation pointeur
  11. template<typename T>
  12. virtual list<T*>::~list()
  13. {
  14. }


 
mais ca compile pas ...


 
Il me semble que tu ne peux pas spécialiser juste une fonction membre seule. Tu dois commencer par spécialiser la classe elle même et à l'interrieur la fonction membre.
 
 

Code :
  1. template<typename T>
  2. class list
  3. {
  4.   // ...
  5.  
  6.   virtual ~list()
  7.   {
  8.   }
  9. };
  10. // spéclialisation pointeur
  11. template<typename T>
  12. class list<T*>
  13. {
  14.   virtual list<T*>::~list()
  15.   {
  16.   }
  17. };


 
Edit : corrections pour que ça compile.


Message édité par Kristoph le 09-02-2004 à 20:33:57
n°636464
blackgodde​ss
vive le troll !
Posté le 09-02-2004 à 21:06:10  profilanswer
 

pourtant ceci compile :
(chez moi, je ne sais pas si c'est standard ...)
 

Code :
  1. template<bool bcrypt = false>
  2. class client_sock
  3. {
  4. void open()
  5. {
  6. }
  7. };
  8. template<>
  9. void client_sock<true>::open()
  10. {
  11. }


---------------
-( BlackGoddess )-
n°636475
Taz
bisounours-codeur
Posté le 09-02-2004 à 21:20:46  profilanswer
 

ça l'est

n°636480
blackgodde​ss
vive le troll !
Posté le 09-02-2004 à 21:24:19  profilanswer
 

ca ne fonctionne pas pareil pour les destructeurs virtuels ?


Message édité par blackgoddess le 09-02-2004 à 21:24:32

---------------
-( BlackGoddess )-
n°636518
blackgodde​ss
vive le troll !
Posté le 09-02-2004 à 22:04:23  profilanswer
 

apparement la spécialisation fonctionne (chez moi toujours) uniquement pour une spécialisation autre que les pointeurs...
est-ce un cas général ou est-ce mon compilo qui a du mal ?


---------------
-( BlackGoddess )-
n°636557
Taz
bisounours-codeur
Posté le 09-02-2004 à 22:32:22  profilanswer
 

c'est quoi ton compilateur ?
les (destructeurs) virtuels ça n'existe pas

n°636566
blackgodde​ss
vive le troll !
Posté le 09-02-2004 à 22:43:00  profilanswer
 

vc++7
 
en fait
 
toujours avec  

Code :
  1. template<typename T>
  2.   class list
  3.   {
  4.       // ...  
  5.      
  6.       virtual ~list()
  7.       {
  8.       }
  9.   };


 

Code :
  1. template<>
  2. list<int>::~list()
  3. {
  4. }


 
fonctionne, mais pas
 

Code :
  1. template<typename T>
  2. list<T*>::~list()
  3. {
  4. }


 
 
j'ai fait un autre test :

Code :
  1. template<typename T>
  2. void t()
  3. {
  4. }
  5. template<typename T>
  6. void t<T*>()
  7. { // error C2768: 't<`template-parameter-257' *>' : explicit template arguments were not expected to be associated with this declaration
  8. }
  9. int main()
  10. {
  11.   t<void>();
  12.   t<void*>();
  13. }


 
la doc de l'erreur sur les msdn : http://msdn.microsoft.com/library/ [...] rC2768.asp
 
serait-ce un défaut du compilo pour cette spécialisation ?
 
(g bcp de mal a trouver de la doc sur la spécialisation pour pointeur sur le net ...)


---------------
-( BlackGoddess )-
n°636583
Taz
bisounours-codeur
Posté le 09-02-2004 à 22:58:46  profilanswer
 

pas de spécialization partielle de fonction template

n°636588
blackgodde​ss
vive le troll !
Posté le 09-02-2004 à 23:01:43  profilanswer
 

erf ca a deja été dit ...
 

Code :
  1. template<typename T>
  2. struct dtor
  3. {
  4. void del()
  5. {
  6. }
  7. };
  8. template<typename T>
  9. struct dtor<T*>
  10. {
  11. void del()
  12. {
  13. }
  14. };


 
compile pas non plus ...
 
j'ai lu que vc++7.1 devait supporter les spécialisations partielles de classes templates, je vais l'installer, on a changé recemment les licenses au taff ...


---------------
-( BlackGoddess )-
n°636596
Taz
bisounours-codeur
Posté le 09-02-2004 à 23:04:31  profilanswer
 

pourtant c'est parfaitement correct./
 
il donne quoi mon premier exemple (premier message) ?

n°636598
blackgodde​ss
vive le troll !
Posté le 09-02-2004 à 23:07:30  profilanswer
 

il fait les mêmes erreurs que mon précédent bout de code, une erreur de syntaxe sur le '>' de 'class Foo< T* >' suivie de quelques autres erreurs qui dérivent de celle la


---------------
-( BlackGoddess )-
n°636602
Taz
bisounours-codeur
Posté le 09-02-2004 à 23:09:21  profilanswer
 

ben tu vas ici http://forum.hardware.fr/hardwaref [...] -46017.htm
 
et tu leur dis que j'avais bien raison dans mon dernier message

n°636607
blackgodde​ss
vive le troll !
Posté le 09-02-2004 à 23:11:12  profilanswer
 

j'ai suivi le topic oui :p
 
ils parlaient de vc++7.1, v l'installer pour voir si ca résoud le pb.


---------------
-( BlackGoddess )-
n°636662
chrisbk
-
Posté le 10-02-2004 à 00:28:19  profilanswer
 

taz a écrit :

ben tu vas ici http://forum.hardware.fr/hardwaref [...] -46017.htm
 
et tu leur dis que j'avais bien raison dans mon dernier message


 
tu t'en es pas remis hein ?
accroches toi, paske :
 

Code :
  1. template<typename T>
  2.   struct dtor
  3.   {
  4.      void del()
  5.      {
  6.      }
  7.   };
  8.  
  9.   template<typename T>
  10.   struct dtor<T*>
  11.   {
  12.      void del()
  13.      {
  14.      }
  15.   };


 
compile tres bien
 

n°636664
chrisbk
-
Posté le 10-02-2004 à 00:30:21  profilanswer
 

D'ailleurs tous tes exemples compilent...
 
Dis, fais pas d'actes desperés hein ? Tu sais, ainsi va le monde, tout change, tout evolue, les vérités deviennent inexactes et tout ca...

n°636717
blackgodde​ss
vive le troll !
Posté le 10-02-2004 à 00:57:22  profilanswer
 

fiou, install finie :)
 
la spécialisation partielle de fonction membres ne fonctionne toujours pas
 

Code :
  1. template<typename T>
  2. class list
  3. {
  4. void del_list()
  5. {
  6. }
  7. };
  8. template<typename T>
  9. void list<T*>::del_list() // erreur
  10. {
  11. }


 
par contre ce qu'a ecrit chrisbk compile en effet, je m'en suis donc tiré comme ca :
 

Code :
  1. template<typename T>
  2. class list
  3. {
  4. template<typename T>
  5. struct tdtor
  6. {
  7.  void del()
  8.  {
  9.   // ...
  10.  }
  11. };
  12. template<typename T>
  13. struct tdtor<T*>
  14. {
  15.  void del()
  16.  {
  17.   // ...
  18.  }
  19. };
  20. tdtor<T> dtor;
  21. public:
  22. virtual ~list()
  23. {
  24.  dtor.del();
  25. }
  26. };


Message édité par blackgoddess le 10-02-2004 à 00:59:43

---------------
-( BlackGoddess )-
mood
Publicité
Posté le   profilanswer
 

 Page :   1  2
Page Précédente

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

  Spécialisation des templates

 

Sujets relatifs
Spécialisation template & Pétage de plombles templates
Chtite question de Templates VS bête tableau en PHP.Question con sur smarty (templates)
[ASP] Templates[C++] Bizarre ces templates ....
[C/C++] inline ds les templatesTemplates PhpBB...
phplib templates : block dans un blockGénération de pages html - templates
Plus de sujets relatifs à : Spécialisation des templates


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