Accès aux classes de base et dérivées

De RAD Studio
Aller à : navigation, rechercher

Remonter à Portée des membres - Index


Lorsque vous déclarez une classe dérivée D, vous énumérez les classes de base B1, B2, ... dans une liste-bases dont le délimiteur est une virgule :

class-key D : base-list { <member-list> }

D hérite de tous les membres de ces classes de base. Les membres des classes de base redéfinies sont obtenus par héritage et sont accessibles via une redéfinition de portée. D ne peut utiliser que des membres public ou protected de ses classes de base. Mais quels vont être les attributs d'accès des membres dérivés tels que les voit D ? D souhaitera, par exemple, utiliser un membre public d'une classe de base, mais le rendre private dans la mesure où des fonctions extérieures sont impliquées. La solution consiste à appliquer des spécificateurs d'accès dans la liste-bases.

Remarque: Puisqu'une classe de base peut être elle-même une classe dérivée, la question de l'attribut d'accès est récursive : vous revenez en arrière jusqu'à ce que vous parveniez à la première des classes de base, celle qui n'a hérité d'aucune autre.

Lorsque vous déclarez D, vous pouvez utiliser le spécificateur d'accès public, protected ou private devant chaque classe de la liste-bases :

class D : public B1, private B2 /* , … */ {
  // …
}

Ces modificateurs ne changent pas les attributs d'accès des membres de base tels qu'ils sont perçus par la classe de base, même s'ils peuvent modifier ceux des membres de base tels que les voit la classe dérivée.

La valeur par défaut est private si D est une déclaration class, et public si D est une déclaration struct.

Remarque: Les unions ne peuvent contenir aucune classe de base ni être utilisées comme classes de base.

La classe dérivée hérite des attributs d'accès d'une classe de base selon les principes suivants :

  • Classe de base public : les membres à accès public de la classe de base sont des membres public de la classe dérivée. Les membres à accès protected de la classe de base sont des membres protected de la classe dérivée. Les membres à accès private de la classe de base restent private pour cette classe.
  • Classe de base protected : les membres à accès public et protected de la classe de base sont des membres protected de la classe dérivée. Les membres à accès private de la classe de base restent des membres private de cette classe.
  • Classe de base private : les membres à accès public et protected de la classe de base sont des membres private de la classe dérivée. Les membres à accès private de la classe de base restent des membres private de cette classe.

Vous remarquerez que les membres private d'une classe de base sont, et restent, inaccessibles aux fonctions membres de la classe dérivée, à moins que vous ne déclariez explicitement un spécificateur friend dans la classe de base pour autoriser l'accès. Par exemple :

/* class X is derived from class A */
class X : A {               // default for class is private A
  // …
}
/* class Y is derived (multiple inheritance) from B and C
   B defaults to private B */
class Y : B, public C {     // override default for C
  // …
}
/* struct S is derived from D */
struct S : D {              // default for struct is public D
  // …
}
/* struct T is derived (multiple inheritance) from D and E
   E defaults to public E */
struct T : private D, E {   // override default for D
                            // E is public by default
  // …
}

Les effets dus aux spécificateurs d'accès dans la liste de base sont adaptables à l'aide d'un nom-qualifié dans les déclarations public ou protected de la classe dérivée. Par exemple :

class B {
   int a;               // private by default
public:
   int b, c;
   int Bfunc(void);
};
class X : private B {   // a, b, c, Bfunc are now private in X
   int d;               // private by default, NOTE: a is not
                        // accessible in X
public:
   B::c;                // c was private, now is public
   int e;
   int Xfunc(void);
};
int Efunc(X& x);        // external to B and X

La fonction Efunc() ne peut utiliser que les noms publics c, e et Xfunc().

La fonction Xfunc() de X, et dérivée de private B, a accès :

  • à c "devenu public"
  • aux membres "private-pour-X" à partir de B : b et Bfunc()
  • aux membres private et public de X : d, e et Xfunc()

Cependant, Xfunc() ne peut pas accéder au membre "private-pour-B", a.

Voir aussi