Newsgroup: it.comp.java
Titolo: passare argomenti al this

ciao a tutti,
vi espongo il problema:
ho una classe, che chiamerò "A", con 2 costruttori: uno a cui NON passo
argomenti e uno a cui passo come argomento un'istanza della classe "C".
ho un'altra classe "B" al cui costruttore devo passare un'istanza di "A"
costruita passando come argometo un'istanza della classe "C".
il problema che la classe B la istanzio all'interno del codice di A (devo
continuare del codice che mi hanno fornito)
nel codice originale non era prevista la classe C quindi per istanziare B
avevo un comando del genere
classeB nome=new classeB(this); //sono all'interno della classeA
esiste un modo per passare a this come argomento classeC??
Grazie per le risposte
Cendo

 classeB nome=new classeB(this); //sono all'interno della classeA
 >
 > esiste un modo per passare a this come argomento classeC??
 >
Sei all'interno della classe A: ma dove?! (vedi sopra)
Se posti qualche spezzone di codice "reale" forse si capisce un po'
meglio qual'e' il tuo problema e magari si trova anche
una soluzione...
Saluti
Roberto

 }

 C?
Dipende...
1) Se C e' una classe derivata da A allora, per ereditarieta', al
    costruttore di B, che prende come parametro un'istanza di A, puoi
    passare anche un'istanza di C:
            class C extends A
            {
              ...
            }
            class A
            {
              private C c;
              ...
              public ... metodo1()
              {
                 ...
                 B b = new B(c)
                 ...
              }
              ...
            }
    In questo caso non e' necessario modificare il codice di B, ma ti
    faccio notare che ci troveremmo di fronte ad un pessimo design, perche' una
    classe base (A) ha una dipendenza diretta con una sua derivata (C): da
    accapponare la pelle! ;)
2) Se C *non* e' una classe derivata da A, si devono seguire altre strade,
    che comportano tutte la modifica del codice esistente:
    2.1) crei un costruttore di B che prende come parametro
         un'istanza di C (oltre che di A, se necessario),
         e lo invochi nel tuo metodo1:
            class B
            {
              private A a;
              private C c;
              ...
              public B(A a, C c)
              {
                this.a = a;
                this.c = c;
                ...
              }
              ...
              public ... faiQualcosaConC()
              {
                 ...
                 c.faiQualcosa();
                 ...
              }
            }
            class A
            {
              private C c;
              ...
              public ... metodo1()
              {
                 ...
                 B b = new B(this, c)
                 ...
              }
              ...
            }
    oppure
    2.2) modifichi l'interfaccia di A per aggiungervi un
         "accessor" che ritorna l'istanza di C associata
         ad A (in generale, pessima soluzione...):
            class A
            {
              private C c;
              ...
              public C getC()
              {
                 return c;
              }
              ...
              public ... metodo1()
              {
                 ...
                 B b = new B(this)
                 ...
              }
              ...
            }
            class B
            {
              private A a;
              ...
              public B(A a)
              {
                 this.a = a;
              }
              ...
              public ... faiQualcosaConC()
              {
                 ...
                 a.getC().faiQualcosa();
                 ...
              }
            }
    oppure
    2.3) modifichi l'interfaccia di A per esporre servizi di
         C, che vengono implementati per delega (molto meglio):
            class A
            {
              private C c;
              ...
              public ... usaC()
              {
                 ...
                 c.faiQualcosa();
                 ...
              }
              ...
              public ... metodo1()
              {
                 ...
                 B b = new B(this)
                 ...
              }
              ...
            }
            class B
            {
              private A a;
              ...
              public B(A a)
              {
                 this.a = a;
              }
              ...
              public ... faiQualcosaConC()
              {
                 ...
                 a.usaC();
                 ...
              }
            }
La soluzione 2.1 si spiega da se'...
La soluzione 2.2 e' utilizzata spessissimo, ma viola spudoratamente
l'incapsulamento di A e per limitare i danni e' normalmente necessario
garantire che l'istanza di C sia ritornata dall'"accessor" in una qualche
forma che la renda "Immutable" da parte di B.
La soluzione 2.3 ha il *grande* vantaggio che non espone a B
l'esistenza di C, permettendo maggiore flessibilita' al design
complessivo del sistema, ma puo' costringere ad effettuare modifiche
"importati" alla interfaccia della classe A.
In verita', e' ben difficile darti una risposta esauriente
perche', non sapendo qual'e' il tuo obiettivo finale, ogni
scelta di design puo' essere giusta o sbagliata...
Saluti
Roberto

 scelta di design puo' essere giusta o sbagliata...
Perfetto, grazie mille.
Cendo