2016-01-13 17 views
5

Si consideri il seguente esempio di codice:Perché le classi annidate sono "ereditate"?

class Outer 
{ 
    public class Nested { } 
} 

class SubOuter : Outer { } 

class Test 
{ 
    Test() 
    { 
     Outer.Nested x;  // Makes sense. 
     SubOuter.Nested y; // Compiles, but why? 
    } 
} 

Sembra che la classe annidata viene "ereditata" dal sottoclasse. Dov'è il punto in questo? Cosa posso fare con questa funzione che non posso (o non posso facilmente) fare diversamente? Non sono Outer.Nested e SubOuter.Nested esattamente equivalenti?

Chiarimento: Certo che compila perché il C# spec dice così. Lo capisco. Sto chiedendo perché C# è stato progettato in questo modo, dal momento che non sembra che aggiunga qualcosa alla lingua. Se hai un esempio in contrario, cioè un codice che diventa più facile/più breve/migliore usando questa funzione, ti preghiamo di condividerla in una risposta e la accetterò volentieri.

+2

perché il 'Nested' è pubblico, quindi la classe' SubOuter' può vederlo nella classe base. –

+2

Dov'è il problema, perché non vuoi che questo venga compilato. –

+1

'Outer.Nested' e' SubOuter.Nested' sono equivalenti, non ci sono differenze in essi tranne il modo di dichiarazione. –

risposta

5

Dal punto di vista di TestNested è solo un identificatore come se fosse un membro, ad es. Siccome è public Puoi accedervi ovunque sia possibile accedere a qualsiasi classe Outer o SubOuter. Tuttavia entrambi gli usi sono identici, identificano la stessa classe.

Si può anche fare riferimento quella dell'altra:

Outer.Nested x = new Outer.Nested(); 
SubOuter.Nested y = x; 

O anche

Outer.Nested x = new SubOuter.Nested(); 
SubOuter.Nested y = x; 

Tuttavia, come si può vedere nel debugger sia x e y condividono un riferimento alla Outer.Nested invece di SubOuter.Nested .

MODIFICA: come già menzionato, questa è la no nuova funzione, è semplicemente il solito trattamento dei membri all'interno delle classi. Pertanto, sicuramente non aggiunge alcun beneficio alla lingua in quanto la funzione come la descrivi semplicemente non esiste. Per questo segue lo Principle of least astonishment.

Il trattamento di classi annidate differenzialmente tuttavia sarebbe una nuova funzionalità.

3

Poiché la classe Nested è pubblica, la classe SubOuter può visualizzarla nella classe base.

E hai ragione. Outer.Nested e SubOuter.Nested sono equivalenti, non vi è alcuna differenza in loro tranne il modo di dichiarazione.

Aggiornamento

secondo il vostro commento che le caratteristiche hanno costi. questa funzione è già implementata in .NET (intendo sottoclasse può vedere i membri pubblici e protetti della classe base) quindi non c'è alcun costo aggiuntivo per implementare questo è. NET.

è possibile considerare la classe Nested come qualsiasi altra proprietà nella classe base.

questo è molto importante spiegare che scritto nei commenti sulla tua domanda da @ Damien_The_Unbeliever.

No, stai chiedendo una nuova funzione. Tutti i membri pubblici di una classe base sono accessibili tramite classi ereditanti. Perché le classi dovrebbero essere trattate in modo diverso rispetto ad es. metodi, e perché il team del compilatore deve aggiungere specificamente il codice per impedirti di effettuare tali accessi? (E poi ottenere il messaggio di errore tradotto in varie lingue, documentarlo, ecc.)

Problemi correlati