=E7a a l'air d'etre un probl=E8me archi connu et rabach=E9, mais je n'ai
pas trouv=E9 la r=E9ponse ni sur la toile ni sur cette mailing
(probablement les mauvais mots clefs).
template <class T>
class A {
friend A<T> operator +<>(A<T>,A<T>);
};
template <class T>
A<T> operator+ (A<T>,A<T>){
}
error: template-id 'operator+<>' does not match any template
declaration
si je retire les vilains <> dans la d=E9claration friend operator :
warning: friend declaration declares a non-template function
template <class T> class A { friend A<T> operator +<>(A<T>,A<T>); };
La méthode canonique serait plutôt :
class C { public: C& operator+= (C const&); };
C operator + (C const& a, C const& b) { C a; a+= b; return a; }
Serge Paccalin
Le samedi 24 novembre 2007 à 01:03:16, Fabien LE LEZ a écrit dans fr.comp.lang.c++ :
On Fri, 23 Nov 2007 08:42:09 -0800 (PST), meow :
template <class T> class A { friend A<T> operator +<>(A<T>,A<T>); };
La méthode canonique serait plutôt :
class C { public: C& operator+= (C const&); };
C operator + (C const& a, C const& b) { C a; a+= b; return a; }
C tmp(a); tmp += b; return tmp;
-- ___________ _/ _ _`_`_`_) Serge PACCALIN -- sp ad mailclub.net _L_) Il faut donc que les hommes commencent -'(__) par n'être pas fanatiques pour mériter _/___(_) la tolérance. -- Voltaire, 1763
Le samedi 24 novembre 2007 à 01:03:16, Fabien LE LEZ a écrit dans
fr.comp.lang.c++ :
On Fri, 23 Nov 2007 08:42:09 -0800 (PST), meow
<schwarz.ben@gmail.com>:
template <class T>
class A {
friend A<T> operator +<>(A<T>,A<T>);
};
La méthode canonique serait plutôt :
class C
{
public:
C& operator+= (C const&);
};
C operator + (C const& a, C const& b)
{
C a;
a+= b;
return a;
}
C tmp(a);
tmp += b;
return tmp;
--
___________
_/ _ _`_`_`_) Serge PACCALIN -- sp ad mailclub.net
_L_) Il faut donc que les hommes commencent
-'(__) par n'être pas fanatiques pour mériter
_/___(_) la tolérance. -- Voltaire, 1763
Le samedi 24 novembre 2007 à 01:03:16, Fabien LE LEZ a écrit dans fr.comp.lang.c++ :
On Fri, 23 Nov 2007 08:42:09 -0800 (PST), meow :
template <class T> class A { friend A<T> operator +<>(A<T>,A<T>); };
La méthode canonique serait plutôt :
class C { public: C& operator+= (C const&); };
C operator + (C const& a, C const& b) { C a; a+= b; return a; }
C tmp(a); tmp += b; return tmp;
-- ___________ _/ _ _`_`_`_) Serge PACCALIN -- sp ad mailclub.net _L_) Il faut donc que les hommes commencent -'(__) par n'être pas fanatiques pour mériter _/___(_) la tolérance. -- Voltaire, 1763
Fabien LE LEZ
On Sat, 24 Nov 2007 10:17:18 +0100, Serge Paccalin :
C tmp(a); tmp += b; return tmp;
Gloups, oui, effectivement. Désolé.
On Sat, 24 Nov 2007 10:17:18 +0100, Serge Paccalin :
On Sat, 24 Nov 2007 10:17:18 +0100, Serge Paccalin :
C tmp(a); tmp += b; return tmp;
Gloups, oui, effectivement. Désolé.
James Kanze
On Nov 23, 5:42 pm, meow wrote:
ça a l'air d'etre un problème archi connu et rabaché, mais je n'a i pas trouvé la réponse ni sur la toile ni sur cette mailing (probablement les mauvais mots clefs).
template <class T> class A { friend A<T> operator +<>(A<T>,A<T>); };
Attention : ici, tu n'as pas déclaré une template comme ami, mais une fonction non-template. Selon la norme, je crois ce que tu veux, c'est :
friend A<T> operator+< A< T > >( A< T >, A< T > ) ;
Seulement, dans ce cas-là, il faudrait une declaration du template de la fonction avant la classe. Quelque chose du genre :
template< typename T > class A ; template< typename T > A< T > operator+( A< T >, A< T > ) ;
template< typename T > class A { friend A< T > operator+< A< T > >( A< T >, A< T > ) ; // ... } ;
Enfin, c'est comme ça que je comprends la norme. Je ne l'ai jamais essayé dans la pratique. Pour le cas des operator arithmetiques binaires, par exemple, je fais quelque chose du genre :
template< typename T > class A : public ArithmeticOperators< A< T > > { public A& operator+=( A const& other ) ; // ... } ;
Le template de classe ArithmeticOperators s'occupe de générer un operator+ (en tant que fonction libre) à partir de l'operator+=.
Plus généralement, dans les templates de classe, j'implémente toutes les fonctionnalités par des fonctions membres, puis je me sers de l'idiome de Barton et Nackman pour en générer des fonctions libres, si j'en ai besoin. Si, par exemple, pour une raison ou une autre (peut-être des questions de performance), je ne voulais pas implémenter operator+ au moyen de l'operator+=, je ferais quelque chose du genre :
template< typename T > class A { public: A add( A const& other ) const ; friend A operator+( A const& lhs, A const& rhs ) { return lhs.add( rhs ) ; } } ;
(Du coup, l'operator + n'est pas un template ! Mais chaque instantiation du template de classe A génèrerait une declaration d'une nouvelle fonction libre. Et une définition, si jamais la fonction est réelement appelée.)
template <class T> A<T> operator+ (A<T>,A<T>){ }
error: template-id 'operator+<>' does not match any template declaration
si je retire les vilains <> dans la déclaration friend operator : warning: friend declaration declares a non-template function
Est-ce que tu aurais un exemple du cas où tu as l'avertissement ? Je m'y attendrais éventuellement pour ce que tu as écrit ci-dessus.
-- James Kanze (GABI Software) email: Conseils en informatique orientée objet/ Beratung in objektorientierter Datenverarbeitung 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
On Nov 23, 5:42 pm, meow <schwarz....@gmail.com> wrote:
ça a l'air d'etre un problème archi connu et rabaché, mais je n'a i
pas trouvé la réponse ni sur la toile ni sur cette mailing
(probablement les mauvais mots clefs).
template <class T>
class A {
friend A<T> operator +<>(A<T>,A<T>);
};
Attention : ici, tu n'as pas déclaré une template comme ami,
mais une fonction non-template. Selon la norme, je crois ce que
tu veux, c'est :
friend A<T> operator+< A< T > >( A< T >, A< T > ) ;
Seulement, dans ce cas-là, il faudrait une declaration du
template de la fonction avant la classe. Quelque chose du
genre :
template< typename T > class A ;
template< typename T > A< T > operator+( A< T >, A< T > ) ;
template< typename T >
class A {
friend A< T > operator+< A< T > >( A< T >, A< T > ) ;
// ...
} ;
Enfin, c'est comme ça que je comprends la norme. Je ne l'ai
jamais essayé dans la pratique. Pour le cas des operator
arithmetiques binaires, par exemple, je fais quelque chose du
genre :
template< typename T >
class A : public ArithmeticOperators< A< T > >
{
public
A& operator+=( A const& other ) ;
// ...
} ;
Le template de classe ArithmeticOperators s'occupe de générer un
operator+ (en tant que fonction libre) à partir de l'operator+=.
Plus généralement, dans les templates de classe, j'implémente
toutes les fonctionnalités par des fonctions membres, puis je me
sers de l'idiome de Barton et Nackman pour en générer des
fonctions libres, si j'en ai besoin. Si, par exemple, pour une
raison ou une autre (peut-être des questions de performance), je
ne voulais pas implémenter operator+ au moyen de l'operator+=,
je ferais quelque chose du genre :
template< typename T >
class A
{
public:
A add( A const& other ) const ;
friend A operator+( A const& lhs, A const& rhs )
{
return lhs.add( rhs ) ;
}
} ;
(Du coup, l'operator + n'est pas un template ! Mais chaque
instantiation du template de classe A génèrerait une declaration
d'une nouvelle fonction libre. Et une définition, si jamais la
fonction est réelement appelée.)
template <class T>
A<T> operator+ (A<T>,A<T>){
}
error: template-id 'operator+<>' does not match any template
declaration
si je retire les vilains <> dans la déclaration friend operator :
warning: friend declaration declares a non-template function
Est-ce que tu aurais un exemple du cas où tu as
l'avertissement ? Je m'y attendrais éventuellement pour ce que
tu as écrit ci-dessus.
--
James Kanze (GABI Software) email:james.kanze@gmail.com
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
ça a l'air d'etre un problème archi connu et rabaché, mais je n'a i pas trouvé la réponse ni sur la toile ni sur cette mailing (probablement les mauvais mots clefs).
template <class T> class A { friend A<T> operator +<>(A<T>,A<T>); };
Attention : ici, tu n'as pas déclaré une template comme ami, mais une fonction non-template. Selon la norme, je crois ce que tu veux, c'est :
friend A<T> operator+< A< T > >( A< T >, A< T > ) ;
Seulement, dans ce cas-là, il faudrait une declaration du template de la fonction avant la classe. Quelque chose du genre :
template< typename T > class A ; template< typename T > A< T > operator+( A< T >, A< T > ) ;
template< typename T > class A { friend A< T > operator+< A< T > >( A< T >, A< T > ) ; // ... } ;
Enfin, c'est comme ça que je comprends la norme. Je ne l'ai jamais essayé dans la pratique. Pour le cas des operator arithmetiques binaires, par exemple, je fais quelque chose du genre :
template< typename T > class A : public ArithmeticOperators< A< T > > { public A& operator+=( A const& other ) ; // ... } ;
Le template de classe ArithmeticOperators s'occupe de générer un operator+ (en tant que fonction libre) à partir de l'operator+=.
Plus généralement, dans les templates de classe, j'implémente toutes les fonctionnalités par des fonctions membres, puis je me sers de l'idiome de Barton et Nackman pour en générer des fonctions libres, si j'en ai besoin. Si, par exemple, pour une raison ou une autre (peut-être des questions de performance), je ne voulais pas implémenter operator+ au moyen de l'operator+=, je ferais quelque chose du genre :
template< typename T > class A { public: A add( A const& other ) const ; friend A operator+( A const& lhs, A const& rhs ) { return lhs.add( rhs ) ; } } ;
(Du coup, l'operator + n'est pas un template ! Mais chaque instantiation du template de classe A génèrerait une declaration d'une nouvelle fonction libre. Et une définition, si jamais la fonction est réelement appelée.)
template <class T> A<T> operator+ (A<T>,A<T>){ }
error: template-id 'operator+<>' does not match any template declaration
si je retire les vilains <> dans la déclaration friend operator : warning: friend declaration declares a non-template function
Est-ce que tu aurais un exemple du cas où tu as l'avertissement ? Je m'y attendrais éventuellement pour ce que tu as écrit ci-dessus.
-- James Kanze (GABI Software) email: Conseils en informatique orientée objet/ Beratung in objektorientierter Datenverarbeitung 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
meow
Bonjour, et merci pour vos réponses. Avant de continuer, je tiens à préciser que mes soucis sont inhérents à la reprise d'un vieux code (bibliothèque de minimisation coool). Pour info, le fichier dans lequel j'ai expérimenté les soucis exposés ici date de 1994 Si ça pe ut aider...
@Fabien, c'est essentiellement l'emploi du template qui complique tout ;)
@Kanze:
Attention : ici, tu n'as pas déclaré une template comme ami, mais une fonction non-template.
Euh, je t'avoues que je ne connais déjà pas cette notation avec les chevrons vides :/ J'ai découvert récemment qu'on pouvait utiliser ce genre d'écriture pour définir une implémentation particulière d'une fonction ou d'une classe déclarée template et dont on souhaite instancier les arguments template...
Selon la norme, je crois ce que tu veux, c'est : friend A<T> operator+< A< T > >( A< T >, A< T > ) ;
J'ai essayé (dans mon cas A = Model et T=Type ), et gcc n'est toujours pas content : (Dans mon exemple j'ai ../../include/coool/Model.hh:226: error: template-id 'operator +<Model<double> >' for 'Model<double> operator+(const Model<double>&, const std::valarray<double>&)' does not match any template declaration
Cela étant, je ne comprends pas ton écriture, et de plus je ne vois pas ce que cela donnerait pour les cas où j'ai des arguments d'autres types que Model<Type>: friend Model<Type> operator+<>(const Model<Type>&, const Model<Type>&); friend Model<Type> operator+<>(const Model<Type>&, const std::valarray<Type>&); friend Model<Type> operator+<>(const std::valarray<Type>&, const Model<Type>&); friend Model<Type> operator*<>(Type, const Model<Type>&);
Et puis il ne faudrait pas spécifier explicitement qu'on a qu'il s'agit d'une fonction template, un truc du genre : template<> friend Model<Type> operator+<Type>(const Model<Type>&, const std::valarray<Type>&); (j'ai l'impression d'etre un singe savant... Avec un peu de chance je réécrirai proust avant d'avoir réussi à faire compiler/fonctionner m a bibliothèque)
Seulement, dans ce cas-là, il faudrait une declaration du template de la fonction avant la classe. Quelque chose du genre :
En effet, c'est d'ailleurs le cas dans le fichier en question. D'ailleurs, j'ai copié collé des sous parties un peu plus bas dans ce message comme tu me l'avais demandé.
Pour le cas des operator arithmetiques binaires, par exemple, je fais quelque chose du genre : Le template de classe ArithmeticOperators s'occupe de générer un operator+ (en tant que fonction libre) à partir de l'operator+=.
Tu veux dire que si dans mon cas je commentes les déclarations et définitions des fonctions libres, le compilo sera assez aimable pour m'en fournir automatiquement a partir des operateurs operation= (+=, *=, ...) de classe ?
Plus généralement, dans les templates de classe, j'implémente toutes les fonctionnalités par des fonctions membres, puis je me sers de l'idiome de Barton et Nackman pour en générer des fonctions libres, si j'en ai besoin. Si, par exemple, pour une raison ou une autre (peut-être des questions de performance), je ne voulais pas implémenter operator+ au moyen de l'operator+=, je ferais quelque chose du genre :
template< typename T > class A { public: A add( A const& other ) const ; friend A operator+( A const& lhs, A const& rhs ) { return lhs.add( rhs ) ; } } ;
Hum, ça me semble séduisant... Donc, remonter les définitions des fonctions libres dans la classe, et supprimer les déclarations templates... Après tout, oui, il n'y a pas de raison que j'utilise cet operateur libre sur des types que je n'aurai pas défini... ça peut fonctionner.
Est-ce que tu aurais un exemple du cas où tu as l'avertissement ? Je m'y attendrais éventuellement pour ce que tu as écrit ci-dessus.
gcc dit ../../include/coool/Model.hh:226: error: template-id 'operator+<>' for 'Model<double> operator+(const Model<double>&, const std::valarray<double>&)' does not match any template declaration
Et la ligne 426 c'est la déclaration friend dans la définition de la classe
---------------------- Et si je comprends bien ta question tu veux aussi savoir ce qui lève le soucis ../../include/coool/Model.hh: In instantiation of 'Model<double>': templates.cc:10: instantiated from here 09 #include "coool/Model.hh" 10 template class Model<double>;
En tous les cas, merci pour le temps et la patience.
Bonjour, et merci pour vos réponses. Avant de continuer, je tiens à
préciser que mes soucis sont inhérents à la reprise d'un vieux code
(bibliothèque de minimisation coool). Pour info, le fichier dans
lequel j'ai expérimenté les soucis exposés ici date de 1994 Si ça pe ut
aider...
@Fabien, c'est essentiellement l'emploi du template qui complique
tout ;)
@Kanze:
Attention : ici, tu n'as pas déclaré une template comme ami,
mais une fonction non-template.
Euh, je t'avoues que je ne connais déjà pas cette notation avec les
chevrons vides :/
J'ai découvert récemment qu'on pouvait utiliser ce genre d'écriture
pour définir une implémentation particulière d'une fonction ou d'une
classe déclarée template et dont on souhaite instancier les arguments
template...
Selon la norme, je crois ce que tu veux, c'est :
friend A<T> operator+< A< T > >( A< T >, A< T > ) ;
J'ai essayé (dans mon cas A = Model et T=Type ), et gcc n'est toujours
pas content :
(Dans mon exemple j'ai
../../include/coool/Model.hh:226: error: template-id 'operator
+<Model<double> >' for 'Model<double> operator+(const Model<double>&,
const std::valarray<double>&)' does not match any template declaration
Cela étant, je ne comprends pas ton écriture, et de plus je ne vois
pas ce que cela donnerait pour les cas où j'ai des arguments d'autres
types que Model<Type>:
friend Model<Type> operator+<>(const Model<Type>&, const
Model<Type>&);
friend Model<Type> operator+<>(const Model<Type>&, const
std::valarray<Type>&);
friend Model<Type> operator+<>(const std::valarray<Type>&,
const Model<Type>&);
friend Model<Type> operator*<>(Type, const Model<Type>&);
Et puis il ne faudrait pas spécifier explicitement qu'on a qu'il
s'agit d'une fonction template, un truc du genre :
template<>
friend Model<Type> operator+<Type>(const Model<Type>&, const
std::valarray<Type>&);
(j'ai l'impression d'etre un singe savant... Avec un peu de chance je
réécrirai proust avant d'avoir réussi à faire compiler/fonctionner m a
bibliothèque)
Seulement, dans ce cas-là, il faudrait une declaration du
template de la fonction avant la classe. Quelque chose du
genre :
En effet, c'est d'ailleurs le cas dans le fichier en question.
D'ailleurs, j'ai copié collé des sous parties un peu plus bas dans ce
message comme tu me l'avais demandé.
Pour le cas des operator
arithmetiques binaires, par exemple, je fais quelque chose du
genre :
Le template de classe ArithmeticOperators s'occupe de générer un
operator+ (en tant que fonction libre) à partir de l'operator+=.
Tu veux dire que si dans mon cas je commentes les déclarations et
définitions des fonctions libres, le compilo sera assez aimable pour
m'en fournir automatiquement a partir des operateurs operation= (+=,
*=, ...) de classe ?
Plus généralement, dans les templates de classe, j'implémente
toutes les fonctionnalités par des fonctions membres, puis je me
sers de l'idiome de Barton et Nackman pour en générer des
fonctions libres, si j'en ai besoin. Si, par exemple, pour une
raison ou une autre (peut-être des questions de performance), je
ne voulais pas implémenter operator+ au moyen de l'operator+=,
je ferais quelque chose du genre :
template< typename T >
class A
{
public:
A add( A const& other ) const ;
friend A operator+( A const& lhs, A const& rhs )
{
return lhs.add( rhs ) ;
}
} ;
Hum, ça me semble séduisant... Donc, remonter les définitions des
fonctions libres dans la classe, et supprimer les déclarations
templates... Après tout, oui, il n'y a pas de raison que j'utilise cet
operateur libre sur des types que je n'aurai pas défini... ça peut
fonctionner.
Est-ce que tu aurais un exemple du cas où tu as
l'avertissement ? Je m'y attendrais éventuellement pour ce que
tu as écrit ci-dessus.
gcc dit
../../include/coool/Model.hh:226: error: template-id 'operator+<>' for
'Model<double> operator+(const Model<double>&, const
std::valarray<double>&)' does not match any template declaration
Et la ligne 426 c'est la déclaration friend dans la définition de la
classe
----------------------
Et si je comprends bien ta question tu veux aussi savoir ce qui lève
le soucis
../../include/coool/Model.hh: In instantiation of 'Model<double>':
templates.cc:10: instantiated from here
09 #include "coool/Model.hh"
10 template class Model<double>;
En tous les cas, merci pour le temps et la patience.
Bonjour, et merci pour vos réponses. Avant de continuer, je tiens à préciser que mes soucis sont inhérents à la reprise d'un vieux code (bibliothèque de minimisation coool). Pour info, le fichier dans lequel j'ai expérimenté les soucis exposés ici date de 1994 Si ça pe ut aider...
@Fabien, c'est essentiellement l'emploi du template qui complique tout ;)
@Kanze:
Attention : ici, tu n'as pas déclaré une template comme ami, mais une fonction non-template.
Euh, je t'avoues que je ne connais déjà pas cette notation avec les chevrons vides :/ J'ai découvert récemment qu'on pouvait utiliser ce genre d'écriture pour définir une implémentation particulière d'une fonction ou d'une classe déclarée template et dont on souhaite instancier les arguments template...
Selon la norme, je crois ce que tu veux, c'est : friend A<T> operator+< A< T > >( A< T >, A< T > ) ;
J'ai essayé (dans mon cas A = Model et T=Type ), et gcc n'est toujours pas content : (Dans mon exemple j'ai ../../include/coool/Model.hh:226: error: template-id 'operator +<Model<double> >' for 'Model<double> operator+(const Model<double>&, const std::valarray<double>&)' does not match any template declaration
Cela étant, je ne comprends pas ton écriture, et de plus je ne vois pas ce que cela donnerait pour les cas où j'ai des arguments d'autres types que Model<Type>: friend Model<Type> operator+<>(const Model<Type>&, const Model<Type>&); friend Model<Type> operator+<>(const Model<Type>&, const std::valarray<Type>&); friend Model<Type> operator+<>(const std::valarray<Type>&, const Model<Type>&); friend Model<Type> operator*<>(Type, const Model<Type>&);
Et puis il ne faudrait pas spécifier explicitement qu'on a qu'il s'agit d'une fonction template, un truc du genre : template<> friend Model<Type> operator+<Type>(const Model<Type>&, const std::valarray<Type>&); (j'ai l'impression d'etre un singe savant... Avec un peu de chance je réécrirai proust avant d'avoir réussi à faire compiler/fonctionner m a bibliothèque)
Seulement, dans ce cas-là, il faudrait une declaration du template de la fonction avant la classe. Quelque chose du genre :
En effet, c'est d'ailleurs le cas dans le fichier en question. D'ailleurs, j'ai copié collé des sous parties un peu plus bas dans ce message comme tu me l'avais demandé.
Pour le cas des operator arithmetiques binaires, par exemple, je fais quelque chose du genre : Le template de classe ArithmeticOperators s'occupe de générer un operator+ (en tant que fonction libre) à partir de l'operator+=.
Tu veux dire que si dans mon cas je commentes les déclarations et définitions des fonctions libres, le compilo sera assez aimable pour m'en fournir automatiquement a partir des operateurs operation= (+=, *=, ...) de classe ?
Plus généralement, dans les templates de classe, j'implémente toutes les fonctionnalités par des fonctions membres, puis je me sers de l'idiome de Barton et Nackman pour en générer des fonctions libres, si j'en ai besoin. Si, par exemple, pour une raison ou une autre (peut-être des questions de performance), je ne voulais pas implémenter operator+ au moyen de l'operator+=, je ferais quelque chose du genre :
template< typename T > class A { public: A add( A const& other ) const ; friend A operator+( A const& lhs, A const& rhs ) { return lhs.add( rhs ) ; } } ;
Hum, ça me semble séduisant... Donc, remonter les définitions des fonctions libres dans la classe, et supprimer les déclarations templates... Après tout, oui, il n'y a pas de raison que j'utilise cet operateur libre sur des types que je n'aurai pas défini... ça peut fonctionner.
Est-ce que tu aurais un exemple du cas où tu as l'avertissement ? Je m'y attendrais éventuellement pour ce que tu as écrit ci-dessus.
gcc dit ../../include/coool/Model.hh:226: error: template-id 'operator+<>' for 'Model<double> operator+(const Model<double>&, const std::valarray<double>&)' does not match any template declaration
Et la ligne 426 c'est la déclaration friend dans la définition de la classe
---------------------- Et si je comprends bien ta question tu veux aussi savoir ce qui lève le soucis ../../include/coool/Model.hh: In instantiation of 'Model<double>': templates.cc:10: instantiated from here 09 #include "coool/Model.hh" 10 template class Model<double>;
En tous les cas, merci pour le temps et la patience.
Fabien LE LEZ
On Mon, 26 Nov 2007 02:09:35 -0800 (PST), meow :
@Fabien, c'est essentiellement l'emploi du template qui complique tout
Il m'avait semblé que le problème venait du mélange de "friend" et de templates. C'est pourquoi je t'indiquais que dans le cas que tu présentes, on n'utilise généralement pas friend, ce qui devrait résoudre ton problème.
On Mon, 26 Nov 2007 02:09:35 -0800 (PST), meow
<schwarz.ben@gmail.com>:
@Fabien, c'est essentiellement l'emploi du template qui complique
tout
Il m'avait semblé que le problème venait du mélange de "friend" et de
templates. C'est pourquoi je t'indiquais que dans le cas que tu
présentes, on n'utilise généralement pas friend, ce qui devrait
résoudre ton problème.
@Fabien, c'est essentiellement l'emploi du template qui complique tout
Il m'avait semblé que le problème venait du mélange de "friend" et de templates. C'est pourquoi je t'indiquais que dans le cas que tu présentes, on n'utilise généralement pas friend, ce qui devrait résoudre ton problème.
meow
Il m'avait semblé que le problème venait du mélange de "friend" et d e templates. C'est pourquoi je t'indiquais que dans le cas que tu présentes, on n'utilise généralement pas friend, ce qui devrait résoudre ton problème.
OK, je ne l'avais pas compris :)
Donc ce que tu préconnisais, c'est de supprimer le friend dans la mesure où on emploie de toute façon des méthodes publiques (les opérateurs définis dans la classe) de la classe pour coder les opérateurs libres. En effet, ça devrait fonctionner (et du coups je me demande meme pourquoi ces fonctions sont déclarées amies), sauf pour certains comme ==, !=, << où des champs privés sont accédés :/=
Il m'avait semblé que le problème venait du mélange de "friend" et d e
templates. C'est pourquoi je t'indiquais que dans le cas que tu
présentes, on n'utilise généralement pas friend, ce qui devrait
résoudre ton problème.
OK, je ne l'avais pas compris :)
Donc ce que tu préconnisais, c'est de supprimer le friend dans la
mesure où on emploie de toute façon des méthodes publiques (les
opérateurs définis dans la classe) de la classe pour coder les
opérateurs libres. En effet, ça devrait fonctionner (et du coups je me
demande meme pourquoi ces fonctions sont déclarées amies), sauf pour
certains comme ==, !=, << où des champs privés sont accédés :/=
Il m'avait semblé que le problème venait du mélange de "friend" et d e templates. C'est pourquoi je t'indiquais que dans le cas que tu présentes, on n'utilise généralement pas friend, ce qui devrait résoudre ton problème.
OK, je ne l'avais pas compris :)
Donc ce que tu préconnisais, c'est de supprimer le friend dans la mesure où on emploie de toute façon des méthodes publiques (les opérateurs définis dans la classe) de la classe pour coder les opérateurs libres. En effet, ça devrait fonctionner (et du coups je me demande meme pourquoi ces fonctions sont déclarées amies), sauf pour certains comme ==, !=, << où des champs privés sont accédés :/=
meow
Oh, tant que j'y suis, je me rends compte qu'il y a deux petites choses évoquées dans ce thread qui ne sont pas claires pour moi et que je n'avais pas remarquées précédemment.
Dans le post de Kanze :
template< typename T > class A : public ArithmeticOperators< A< T > > { public A& operator+=( A const& other ) ; // ... } ;
tu voulais dire A<T>& operator +=(A<T> const& other) ? Ou bien ton ecriture est elle aussi valide ?
Et dans mon post, je me rends compte que je ne comprends pas le fichier template.cc qui lève l'erreur :
#include "coool/Model.hh" template class Model<double>;
C'est quoi cette utilisation du mot clef template ? Et concrètement, qu'est-ce qu'on fait là ? a cette ligne ? Une tentative de deviner : on déclare l'existence d'une classe Model<double>, et on force ce faisant l'instantiation du template par le compilo ?
Ou plus loin
template double std::min(const DiagMatrix<double>&m); la présence du std me trouble... j'ai bien trouvé une fonction libre min avec une signature compatible dans le fichier DiagMatrix.cc, mais point de std... Je suis dubitatif.
Oh, tant que j'y suis, je me rends compte qu'il y a deux petites
choses évoquées dans ce thread qui ne sont pas claires pour moi et que
je n'avais pas remarquées précédemment.
Dans le post de Kanze :
template< typename T >
class A : public ArithmeticOperators< A< T > >
{
public
A& operator+=( A const& other ) ;
// ...
} ;
tu voulais dire A<T>& operator +=(A<T> const& other) ? Ou bien ton
ecriture est elle aussi valide ?
Et dans mon post, je me rends compte que je ne comprends pas le
fichier template.cc qui lève l'erreur :
#include "coool/Model.hh"
template class Model<double>;
C'est quoi cette utilisation du mot clef template ? Et concrètement,
qu'est-ce qu'on fait là ? a cette ligne ? Une tentative de deviner :
on déclare l'existence d'une classe Model<double>, et on force ce
faisant l'instantiation du template par le compilo ?
Ou plus loin
template double std::min(const DiagMatrix<double>&m);
la présence du std me trouble... j'ai bien trouvé une fonction libre
min avec une signature compatible dans le fichier DiagMatrix.cc, mais
point de std... Je suis dubitatif.
Oh, tant que j'y suis, je me rends compte qu'il y a deux petites choses évoquées dans ce thread qui ne sont pas claires pour moi et que je n'avais pas remarquées précédemment.
Dans le post de Kanze :
template< typename T > class A : public ArithmeticOperators< A< T > > { public A& operator+=( A const& other ) ; // ... } ;
tu voulais dire A<T>& operator +=(A<T> const& other) ? Ou bien ton ecriture est elle aussi valide ?
Et dans mon post, je me rends compte que je ne comprends pas le fichier template.cc qui lève l'erreur :
#include "coool/Model.hh" template class Model<double>;
C'est quoi cette utilisation du mot clef template ? Et concrètement, qu'est-ce qu'on fait là ? a cette ligne ? Une tentative de deviner : on déclare l'existence d'une classe Model<double>, et on force ce faisant l'instantiation du template par le compilo ?
Ou plus loin
template double std::min(const DiagMatrix<double>&m); la présence du std me trouble... j'ai bien trouvé une fonction libre min avec une signature compatible dans le fichier DiagMatrix.cc, mais point de std... Je suis dubitatif.
Fabien LE LEZ
On Mon, 26 Nov 2007 05:34:43 -0800 (PST), meow :
(et du coups je me demande meme pourquoi ces fonctions sont déclarées amies), sauf pour certains comme ==, !=, << où des champs privés sont accédés :/
Pour == et !=, as-tu une raison particulière pour préférer une fonction non-membre amie à une fonction membre ?
class A { public: bool operator == (A const&) const; };
Pour <<, généralement, on passe par une fonction membre Print(ostream&). Toutefois, commence par te demander si tu as réellement besoin d'accéder à des membres privés. En effet, << a pour rôle d'afficher à l'écran (ou autre ostream) l'état observable de l'objet ; logiquement, toutes les données qu'il affiche devrait être accessibles (au moins en lecture) par du code extérieur (i.e. via l'interface publique).
On Mon, 26 Nov 2007 05:34:43 -0800 (PST), meow :
(et du coups je me
demande meme pourquoi ces fonctions sont déclarées amies), sauf pour
certains comme ==, !=, << où des champs privés sont accédés :/
Pour == et !=, as-tu une raison particulière pour préférer une
fonction non-membre amie à une fonction membre ?
class A
{
public:
bool operator == (A const&) const;
};
Pour <<, généralement, on passe par une fonction membre
Print(ostream&). Toutefois, commence par te demander si tu as
réellement besoin d'accéder à des membres privés. En effet, << a pour
rôle d'afficher à l'écran (ou autre ostream) l'état observable de
l'objet ; logiquement, toutes les données qu'il affiche devrait être
accessibles (au moins en lecture) par du code extérieur (i.e. via
l'interface publique).
(et du coups je me demande meme pourquoi ces fonctions sont déclarées amies), sauf pour certains comme ==, !=, << où des champs privés sont accédés :/
Pour == et !=, as-tu une raison particulière pour préférer une fonction non-membre amie à une fonction membre ?
class A { public: bool operator == (A const&) const; };
Pour <<, généralement, on passe par une fonction membre Print(ostream&). Toutefois, commence par te demander si tu as réellement besoin d'accéder à des membres privés. En effet, << a pour rôle d'afficher à l'écran (ou autre ostream) l'état observable de l'objet ; logiquement, toutes les données qu'il affiche devrait être accessibles (au moins en lecture) par du code extérieur (i.e. via l'interface publique).
Fabien LE LEZ
On Mon, 26 Nov 2007 06:27:34 -0800 (PST), meow :
Dans le post de Kanze :
Pourquoi n'y réponds-tu pas directement, au lieu de poster en réponse à ton propre message ?
On Mon, 26 Nov 2007 06:27:34 -0800 (PST), meow
<schwarz.ben@gmail.com>:
Dans le post de Kanze :
Pourquoi n'y réponds-tu pas directement, au lieu de poster en réponse
à ton propre message ?