IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Langage C++ Discussion :

template et typedefs


Sujet :

Langage C++

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre averti
    Profil pro
    Inscrit en
    Mai 2005
    Messages
    12
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mai 2005
    Messages : 12
    Par défaut template et typedefs
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
     
    template < typename A, typename B >
    struct Item
    {
    	void Do()
    	{
    		cout << "Hello World !" << endl;
    	}
    };
     
    template < typename A = void, typename B = void >
    class Function
    {
    	typedef vector< Item< A, B > > Array;
    	typedef vector< Item< A, B > >::iterator Iterator;
     
    	Array array;
     
    public:
    	Function();
    	void operator()();
    };
     
    template < typename A, typename B >
    Function< A, B >::Function()
    {
    	array.push_back(Item< A ,B >());
    	array.push_back(Item< A ,B >());
    	array.push_back(Item< A ,B >());
    }
     
    template < typename A, typename B >
    void Function< A, B >::operator()()
    {
    	for(Iterator it = array.begin(); it != array.end(); it++)
    		it->Do();
    }
     
    int main(int argc, char** argv)
    {
    	Function< > f;
    	f();
     
    	return 0;
    }
    Ce code est censé afficher 3 fois "Hello World !" mais il refuse de compiler :

    % g++ main.cpp
    main.cpp:45: erreur: type `std::vector<Item<A, B>, std::allocator<Item<A, B> > >' is not derived from type `Function<A, B>'
    main.cpp:45: erreur: expected `;' before `Iterator'
    main.cpp: In member function 'void Function<A, B>::operator()()':
    main.cpp:65: erreur: 'Iterator' was not declared in this scope
    main.cpp:65: erreur: expected `;' before `it'
    main.cpp:65: erreur: 'it' was not declared in this scope

    Voici ma configuration :

    % g++ -v
    Utilisation des specs internes.
    Target: i486-linux-gnu
    Configuré avec: ../src/configure -v --enable-languages=c,c++,fortran,objc,obj-c++,treelang --prefix=/usr --enable-shared --with-system-zlib --libexecdir=/usr/lib --without-included-gettext --enable-threads=posix --enable-nls --program-suffix=-4.1 --enable-__cxa_atexit --enable-clocale=gnu --enable-libstdcxx-debug --enable-mpfr --enable-checking=release i486-linux-gnu
    Modèle de thread: posix
    version gcc 4.1.2 (Ubuntu 4.1.2-0ubuntu4)

    Le plus étrange est que l'utilisation d'une class Item simple (non template) permet au code de compiler :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
     
    struct Item
    {
    	void Do()
    	{
    		cout << "Hello World !" << endl;
    	}
    };
     
    template < typename A = void, typename B = void >
    class Function
    {
    	typedef vector< Item > Array;
    	typedef vector< Item >::iterator Iterator;
     
    	Array array;
     
    public:
    	Function();
    	void operator()();
    };
     
    template < typename A, typename B >
    Function< A, B >::Function()
    {
    	array.push_back(Item());
    	array.push_back(Item());
    	array.push_back(Item());
    }
     
    template < typename A, typename B >
    void Function< A, B >::operator()()
    {
    	for(Iterator it = array.begin(); it != array.end(); it++)
    		it->Do();
    }
     
    int main(int argc, char** argv)
    {
    	Function< > f;
    	f();
     
    	return 0;
    }
    Si vous avez une idée pour corriger la première version je suis preneur.

  2. #2
    Rédacteur/Modérateur
    Avatar de JolyLoic
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2004
    Messages
    5 463
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 50
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2004
    Messages : 5 463
    Par défaut
    Iterator est un nom qui dépend des paramètres templates. Le compilateur ne peut donc pas savoir s'il s'agit d'un type ou d'une variable (il pourrait y avoir des spécialisations). Il faut donc l'aider un peu :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    for(typename Iterator it = array.begin(); it != array.end(); it++)
    		it->Do();
    Ma session aux Microsoft TechDays 2013 : Développer en natif avec C++11.
    Celle des Microsoft TechDays 2014 : Bonnes pratiques pour apprivoiser le C++11 avec Visual C++
    Et celle des Microsoft TechDays 2015 : Visual C++ 2015 : voyage à la découverte d'un nouveau monde
    Je donne des formations au C++ en entreprise, n'hésitez pas à me contacter.

  3. #3
    Membre chevronné
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2006
    Messages
    366
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Mai 2006
    Messages : 366
    Par défaut
    Je l'aurais plutôt mis au niveau du typedef d'Iterator, sinon ça compilera pas :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    template < typename A = void, typename B = void >
    class Function
    {
    	typedef vector< Item< A, B > > Array;
            typedef typename vector<Item<A, B> >::iterator Iterator;
    //Etc ...

  4. #4
    Alp
    Alp est déconnecté
    Expert confirmé

    Avatar de Alp
    Homme Profil pro
    Inscrit en
    Juin 2005
    Messages
    8 575
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations forums :
    Inscription : Juin 2005
    Messages : 8 575
    Par défaut
    +1.

    Regarde dans la FAQ C++ page templates, le problème est expliqué, ainsi que sa solution.

  5. #5
    Rédacteur/Modérateur
    Avatar de JolyLoic
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2004
    Messages
    5 463
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 50
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2004
    Messages : 5 463
    Par défaut
    +1... C'qu'on peut dire comme bêtises quand même...
    Ma session aux Microsoft TechDays 2013 : Développer en natif avec C++11.
    Celle des Microsoft TechDays 2014 : Bonnes pratiques pour apprivoiser le C++11 avec Visual C++
    Et celle des Microsoft TechDays 2015 : Visual C++ 2015 : voyage à la découverte d'un nouveau monde
    Je donne des formations au C++ en entreprise, n'hésitez pas à me contacter.

  6. #6
    Alp
    Alp est déconnecté
    Expert confirmé

    Avatar de Alp
    Homme Profil pro
    Inscrit en
    Juin 2005
    Messages
    8 575
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations forums :
    Inscription : Juin 2005
    Messages : 8 575
    Par défaut
    Citation Envoyé par JolyLoic Voir le message
    +1... C'qu'on peut dire comme bêtises quand même...

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Parametre template et typedef d'une base
    Par NiamorH dans le forum Langage
    Réponses: 4
    Dernier message: 21/11/2007, 03h09
  2. template et typedef
    Par bolhrak dans le forum Langage
    Réponses: 5
    Dernier message: 09/11/2007, 14h37
  3. Typedef sur fonction template
    Par mchk0123 dans le forum Langage
    Réponses: 7
    Dernier message: 01/04/2007, 15h07
  4. Template typedef, gni :/
    Par Groove dans le forum Langage
    Réponses: 5
    Dernier message: 22/02/2007, 19h11
  5. Réponses: 5
    Dernier message: 17/06/2005, 19h26

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo