Newsgroup: it.comp.lang.c++
Titolo: Perche'? (Accesso a fun protected)

Non capisco la logica che mi impedisce di accedere alle funzioni protected di una mia classe base su un'altro oggetto, ma mi permette di accedere alle funzioni della mia stessa classe.
Mi spiego meglio con un esempio:
class A {
protected:
 void f() {}
};
class B : public A{
protected:
 void h(A* This) {
  This->f();     <--- Questo non compila
  static_cast<B*>(This)->z();} <--- Questo compila
 void z() {}
};
Posso aggirare questo comportamento semplicemente creando un'altra funzione g nella classe B che non fa altro che chiamare la funzione f della classe base; e sostituire la chiamata che non compila con  static_cast<B*>(This)->g();
ma quello che non capisco è:
qual'è la logica che ha portato a questo comportamento?
qual'è l'utilità di avere una situazione così incoerente?
Grazie.

qual'è l'utilità di avere una situazione così incoerente?
Tu puoi accedere alle parti della classe base dichiarate
"protected" solo per la tua stessa istanza (usando "this").
Non e' corretto accedere alle parti "protected" usando un
puntatore ad un'altra istanza perche' (essendo protected)
il loro significato potrebbe non essere quello che credi
visto che questa istanza potrebbe essere di un'altra classe
derivata che non conosci.
Se non ci fosse questo limite allora "protected" vorrebbe
dire veramente pochissimo. Per "aggirare" il controllo
infatti basterebbe dichiarare una propria classe di
appoggio che deriva dalla classe base e che fa da passacarte...
... et voila' ...
tutti i dati e i metodi protected sarebbero accessibili
come se fossero "public".
E in ogni caso...  perche' stai usando protected ? E'
qualcosa che si usa veramente di rado ... le implementazioni
pulite si basano spesso solo su "private" e "public".
Andrea
--
Andrea Griffini, Programmer
http://www.netservers.com/~agriff

   static_cast<B*>(This)->z();} <--- Questo compila
Qui hai semplicemente eseguito un downcast lecito ma non controllato;
Lecito: in quanto B deriva publicamente da A.
Nono controllato: In quanto non sei sicuro che il puntatore punti
effettivamente ad un oggetto di tipo B il che potrebbe portare l'applicativo  alla catastrofe se cosi' non fosse
IMHO  e' consigliato l'uso di dynamic_cast.
--
Ivan Molella
__LINUX__ the choice of the  __GNU__ generation

 Non capisco la logica che mi impedisce di accedere alle funzioni protected di una mia classe base su un'altro oggetto, ma mi permette di accedere alle funzioni della mia stessa classe.
I criteri di visibilita` dei membri di una classe funzionano a livello di 
classe, non di istanza o gerarchia. B puo` accedere a tutti i membri di
*propri* una istanza di B, e a quelli pubblici e protetti ereditati ma
non puo` accedere che solo ai membri pubblici di istanze di un'altra classe 
anche se si tratta di una classe base.
Paolo
--
Paolo Marotta
Home: 
http://web.tiscalinet.it/paolo_marotta
Master's Level in C++ Certified by Brainbench
http://www.brainbench.com/transcript.jsp?pid=2440649

 "protected" solo per la tua stessa istanza (usando "this").
Anche per le altre istanze della stessa classe, in C++ il
controllo di accesso funziona a livello di classe e non di
istanza.
Esempio:
class A {
protected:
  void f();
};
class C : public A {};
class B : public A {
  void g( A* pa, B* pb, C* pc ) {
    this->f();    // Ok
    pa->f();      // ERRORE
    pb->f();      // Ok
    pc->f();      // ERRORE
    pa = this;
    pa->f();      // ERRORE
  }
};
	Mauro

pulite si basano spesso solo su "private" e "public".
non sono un esperto di analisi e design, però mi viene in mente almeno
un esempio in cui è utile protected. Immagina di avere un sistema che
gestisce una GUI:
enum Message { Paint, Click, KeyPressed };
class Window {
public:
	void SendMessage(Message m) { if (m==Paint) this->OnPaint(); }
protected:
	virtual void OnPaint() { ... }
};
class Button: public Window {
protected:
	void OnPaint() { ... }
};
Oppure è un design sbagliato? Ve lo chiedo perché una volta avevo
fatto una cosa simile (anche se non con protected, dato che
programmavo in Turbo Pascal with objects); ci sono dei metodi
migliori?
Anto
--
Antonio Cuni, 19 anni, studente
Brainbench C++ Master: 4.6, higher than 98% of all previous test takers.
C Language: 3.32, higher than 79% of all previous test takers.
Guida C/C++ di Programmazione.it: 
http://cpp.programmazione.it

 Paolo> 
Credo di aver capito.
In pratica la chiamata This->f() accede al membro f() della classe A che è dichiarato protected e quindi non è accessibile se non dallo stesso oggetto di una classe derivata; mentre static_cast<B*>(This)->z() accede al membro f() della classe B (che lo ha ereditato dalla classe A), e quindi è
accessibile.
Grazie.