2009-10-22 10 views
7

Mam problemy z implementacją zagnieżdżonej klasy, której konstruktor jest zainicjowany przez część prywatnych elementów danych klasy otaczającej.Zagnieżdżone prywatne klasy danych "dostęp do prywatnych danych należących do klasy"

Przykład:

Header File: 
class Enclosing { 
    //...Public members 
    //...Private members 
    int x, int y 
    class Inner; // Declaration for nested class 
}; 

Impl. File: 
// Stuff... 
class Enclosing::Inner { 
    explicit Inner() : foo(x), bar(y) // foo and bar are data members of Inner 
    //... 
}; 

pojawia się błąd invalid use of non-static data member. Czy jest coś, czego mi brakuje, jeśli chodzi o zagnieżdżony dostęp do klas dla członków swojej klauzuli?

Odpowiedz

18

Członek x i y są non-static członek danych Enclosing, co oznacza, że istnieją tylko w obrębie konkretnego obiektu klasy Enclosing. Bez konkretnego obiektu nie istnieje ani x ani . Tymczasem próbujesz odwołać się do x i y bez obiektu. Tego nie da się zrobić, o czym próbuje ci opowiedzieć kompilator.

Jeśli chcesz zainicjować członków Inner::foo i Inner::bar z x i y, trzeba przekazać konkretny przedmiot Enclosing wpisać w Inner s konstruktora. Na przykład:

class Enclosing::Inner {  
    explicit Inner(const Enclosing& e) : foo(e.x), bar(e.y) 
    {} 
    //... 
}; 

Dodatkowa uwaga: w oryginalnym C++ 98 klasa wewnętrzna nie ma żadnych specjalnych uprawnień dostępu do zewnętrznej klasy. W kompilatorze C++ 98 musisz albo nadać klasie wewnętrznej niezbędne uprawnienia (przyjaźń), albo ujawnić członków jako publicznie dostępne. Jednak ta sytuacja została zaklasyfikowana jako defect w C++ 98 i zdecydowano, że klasy wewnętrzne powinny mieć pełny dostęp do zewnętrznych członków klasy (nawet prywatnych). Tak więc, czy musisz zrobić coś ekstra w odniesieniu do uprawnień dostępu zależy od Twojego kompilatora.

+1

Dzięki. Czytałem o defekcie w C++ 98 podczas samodzielnego badania i nie byłem pewien, co z tym zrobić. Dzięki za oczyszczenie wszystkiego. – trikker

8

Problem z kodem jest not visibility, jak podkreślił AndreyT, ale to instancja klasy Inner nie jest związany z konkretną instancją klasy Enclosing. Innymi słowy, przy konstruowaniu kompilatora nie można ustalić, który obiekt ma przyjmować wartości od x i y.

Trzeba będzie wyraźnie przewidywać wystąpienie klasy Enclosing do konstruktora klasy Inner jako tak:

class Enclosing 
{ 
private: 
    int x; 
    int y; 

    class Inner 
    { 
    private: 
    int foo; 
    int bar; 

    public: 
    explicit Inner(const Enclosing& e) 
     : foo(e.x), bar(e.y) 
    { } 
    }; 
}; 
0

klasa zagnieżdżona nie może uzyskać dostępu do elementu danych privet od załączając class.compiler pokazać błąd, jeśli staramy się uzyskać dostęp do elementu zamykającego ligustr z klasy, może uzyskać dostęp do danych tylko element publicznej otaczającej klasy .....

Powiązane problemy