Salut,
Pour une fois, c'est moi qui vient avec un problème de template.
Soit une classe de base "classique" sous la forme de
A laquelle on rajoute deux classe template, l'une sous la forme de
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11 class Base{ public: Base(){} /* interdisons la copie et l'affectation (C++11 inside) */ Base(Base const &) = delete; Base & operator = (Base const&) = delete; /* défini dans le cpp, ne fait strictement rien */ virtual ~Base(); virtual void foo() = 0; virtual void bar() = 0; };
et deux tag simples
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5 template <typename T1, typename T2> class Derivee1; template <typename T1> class Derivee2;Si je définis Derivee1 sous la forme de
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3 struct tag1{}; struct tag2{};
derivee1.h
je peux déporter la spécialisation (partielle ou totale) de foo dans un fichier d'instanciation explicit:
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6 template <typename T1, typename T2> class Derivee1 : public Base{ public: void foo(); void bar(); };
derivee_explicit.cpp
[EDIT]
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10 template <> void Derivee1<tag1, tag2>::foo(){ std::cout<<"ca marche"; } template <> void Derivee1<tag1, tag2>::bar(){ std::cout<<"Si ca va pour l'un, ca va pour l'autre"; } template class Derivee1<tag1, tag2>;
Notez que cela fonctionne aussi très bien avec une spécialisation partielle : si je définissait template<typename T1> class Derivee1<T1,tag2>, ca marcherrait
[/EDIT]
Si je fournis directement une spécialisation totale sous une forme proche de
Derive2OK.h
Par contre, si j'essaye de mixer les deux (spécialisation totale et export de la fonction)
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11 template<> class Derivee2<tag1> : public Base{ public: Derivee2(){} void foo(){ std::cout<<"ca marche"; } void bar(){ std::cout<<"Si ca va pour l'un, ca va pour l'autre"; } };
Derivee2KO.hderivee2_explicit.cpp
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8 template<> class Derivee2<tag2> : public Base{ public: Derivee1(){} void foo(); void bar(); };
Je dois avoir oublié quelque chose, mais quoi
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10 template <> void Derivee<tag2>::foo(){ std::cout<<"Ben non, justement"; } template <> void Derivee1<tag2>::bar(){ std::cout<<"Le compilateur ne trouve pas les prototypes"; } template class Derivee2<tag2>;
Partager