2009-08-31 15 views
17

In risposta alla domanda What is your longest-held programming assumption that turned out to be incorrect?, una delle ipotesi sbagliate era:Puoi spiegare questa cosa sull'incapsulamento?

Che variabili membro private erano privato all'istanza e non la classe .

(Link)

Non riuscivo a cogliere ciò che sta parlando, chiunque può spiegare che cosa è sbagliato/ragione su questo con un esempio?

+0

Come questo è correlato all'incapsulamento? – p4bl0

+6

visibilità privata è come l'incapsulazione viene implementata in linguaggi come Java, C++ e C# –

+1

@ p4bl0 Come sono correlati l'incapsulamento e l'ambito della variabile? Piuttosto fondamentalmente. – meagar

risposta

35
public class Example { 
    private int a; 

    public int getOtherA(Example other) { 
    return other.a; 
    } 
} 

In questo modo. Come puoi vedere, il privato non protegge il membro dell'istanza dall'accesso da un'altra istanza.

BTW, questo non è niente male finché si è un po 'attenti. Se privato non funzionasse come nell'esempio precedente, sarebbe ingombrante scrivere equals() e altri metodi simili.

+3

In modo che i membri privati ​​siano privati ​​della classe e un'istanza possa accedere al membro privato di un'altra istanza, correggere? –

+0

Sì, è corretto. –

+0

OK, grazie mille! –

2

codice di esempio (Java):

public class MutableInteger { 
    private int value; 

    // Lots of stuff goes here 

    public boolean equals(Object o) { 
     if(!(o instanceof MutableInteger)){ return false; } 
     MutableInteger other = (MutableInteger) o; 
     return this.value == other.value; // <------------ 
    } 
} 

Se l'ipotesi "variabili membro private sono private all'istanza" fosse corretta, la linea tracciata causerebbe un errore di compilazione, perché il campo other.value è privato e parte di un oggetto diverso da quello in cui viene chiamato il metodo equals().

Ma dal momento che in Java (e nella maggior parte delle altre lingue con il concetto di visibilità) private visibilità è per classe, l'accesso al campo è consentito a tutto il codice dello MutableInteger, irrilevante di quale istanza è stata utilizzata per invocarlo.

+2

"e tutti gli altri linguaggi che hanno il concetto di visibilità, penso" In ruby ​​private è per oggetto. – sepp2k

+0

Grazie per l'informazione, Michael. –

+0

In Scala puoi aggiungere il contesto: privato [this] – egaga

3

Ecco l'equivalente di Michael Borgwardt's answer per quando si è non in grado di accedere ai campi privati ​​della altro oggetto:

public class MutableInteger { 
    private int value; 

    // Lots of stuff goes here 

    public boolean equals(Object o) { 
     if(!(o instanceof MutableInteger)){ return false; } 
     MutableInteger other = (MutableInteger) o; 
     return other.valueEquals(this.value); // <------------ 
    } 

    @Override // This method would probably also be declared in an interface 
    public boolean valueEquals(int oValue) { 
     return this.value == oValue; 
    } 
} 

Oggi questo è noto a programmatori Ruby, ma io ho fatto questo in Java per un po. Preferisco non fare affidamento sull'accesso ai campi privati ​​di un altro oggetto. Ricorda che l'altro oggetto può appartenere a una sottoclasse, che potrebbe memorizzare il valore in un campo oggetto diverso, o in un file o database, ecc.

Problemi correlati