2010-06-01 4 views
4

Compte tenu des classes suivantes:Problème d'accès à l'élément de base dans le constructeur dérivé

class Foo 
{ 
    struct BarBC 
    { 
    protected: 
     BarBC(uint32_t aKey) 
      : mKey(aKey) 
       mOtherKey(0) 

    public: 
     const uint32_t mKey; 
     const uint32_t mOtherKey; 
    }; 


    struct Bar : public BarBC 
    { 
     Bar(uint32_t aKey, uint32_t aOtherKey) 
      : BarBC(aKey), 
       mOtherKey(aOtherKey) // Compile error here 
    }; 
}; 

Je reçois une erreur de compilation au point indiqué:

error: class `Foo::Bar' does not have any field named `mOtherKey'. 

Quelqu'un peut-il expliquer cela? Je suspecte que c'est un problème syntaxique dû à ma classe Bar étant définie dans la classe Foo, mais n'arrive pas à trouver un moyen de contourner le problème.

Il s'agit d'un héritage public simple. Par conséquent, mOtherKey doit être accessible à partir du constructeur Bar. Droite?

Ou est-ce quelque chose à voir avec le fait que mOtherKey est const et je l'ai déjà initialisé à 0 dans le constructeur BarBC?

Répondre

8

Vous ne pouvez pas initialiser les membres d'une classe de base via une liste d'initialisation de membres, uniquement des classes de base directes et virtuelles et des membres de données non statiques de la classe elle-même.
paramètres additionnels à la classe de base constructeur à la place:

struct BarBC { 
    BarBC(uint32_t aKey, uint32_t otherKey = 0) 
     : mKey(aKey), mOtherKey(otherKey) 
    {} 
    // ... 
}; 

struct Bar : public BarBC { 
    Bar(uint32_t aKey, uint32_t aOtherKey) 
     : BarBC(aKey, aOtherKey) 
    {} 
}; 
+0

@George - merci. J'essayais d'initialiser par défaut tous les membres de données const dans le constructeur de la classe de base (pour éviter une erreur de compilation), puis de définir les membres spécifiques à la classe dérivée dans les constructeurs dérivés (tout en laissant les membres dans la classe de base). Pas la meilleure structure de classe par aucune mesure. Mais je n'avais pas réalisé que la liste des initialiseurs avait des restrictions comme celle-ci. – LeopardSkinPillBoxHat

1

Vous ne pouvez pas faire cela comme BarBC construit le mOtherKey - vous ne pouvez pas l'ignorer.

Vous avez soit d'attribuer une nouvelle valeur:

Bar(...) : ... 
{ mOtherKey=aOtherKey; } 

Ou créer constructeur BarBC supplémentaire qui a un paramètre de mOtherKey

Questions connexes