9
votes

Comment accéder à un constructeur privé dans une classe distincte?

J'écris une bibliothèque en C ++. J'ai deux classes dans ma bibliothèque, a code> et b code>. Je veux masquer le constructeur a () code> de n'importe quel code qui fait référence à ma bibliothèque. Je veux aussi la classe B code> pour pouvoir appeler le a () code> constructeur.

Je viens d'un fond C # et souvenez-vous que peu de mon C ++. En C #, je déclarerais simplement déclarer le constructeur a () code> comme interne code>. J'ai lu que le moyen le plus proche de le faire en C ++ est une combinaison de d'ami code> déclarations et déclarations prospectives. Comment puis-je faire cela? Voici mes trois fichiers ci-dessous: P>

AH: P>

public: friend class B;


0 commentaires

4 Réponses :


0
votes

Vous pouvez faire un ami d'un ami de: xxx


0 commentaires

6
votes

Vous devez probablement juste laisser tomber le "externe" de votre troisième tentative de la transformer en une déclaration en avant. Essayez:

a.h: xxx


7 commentaires

La déclaration à terme est probablement ce qu'il manquait.


C'était ça. Merci! Est-il possible de faire uniquement le createa () fonctionner un ami et non la classe entière?


@ user2023861: oui c'est. Vous copieriez essentiellement la signature de fonction complète (portée incluse) et placer ami devant celui-ci. Par exemple: ami A B :: Createa ();


@Zachowland qui ne fonctionnera pas comme B n'est qu'en avance déclaré. Et vous ne pouvez pas définir b avant a car vous n'avez déjà besoin a puisque vous le renvoyez Createa .


J'étais sur le point de dire que cela n'a pas compilé. Ce n'est pas une exigence que seule la fonction est un ami. Je vais garder la classe comme un ami. Merci encore!


@DanielEfrey: Vous devez changer de choses autour (et vous ne pouvez pas le faire en ligne), mais oui, cela peut être fait. Voir mon édition ci-dessous.


@Zachowland d'euh! Bien sûr. Je pensais aussi que cela devrait fonctionner mais je voulais être sûr que je l'ai essayé et j'ai fait une typo stupide. Oui, vous avez raison, cela peut être fait.



1
votes

Sauf absolument nécessaire, vous devez avoir a code> construire lui-même (ou avoir une usine qui crée a code>). Si vous voulez vraiment B code> pour le faire:

class A;

class B
{
public:
    A CreateA();
};

class A
{
private:
    A() {}
    friend class A B::CreateA();
};

A B::CreateA()
{
    A a;
    return a;
}

int main()
{
    B b;
    A a = b.CreateA();
    return 0;
}


2 commentaires

Friend Class A B :: Createa (); <- Pourquoi avez-vous dû ajouter une clé de classe avant A je me demande? Je veux dire n'est pas ça redondant?


@Angelusmortis Vous indiquez que B est un ami de A , pas que a est une classe d'amis.



1
votes

Vous n'avez pas besoin du mot clé externe . Faites-le simple: xxx

Exemple en direct .


0 commentaires