Codice:
public class A
{
static int a;
int b;
public A() {
this(++a);
}
public A(int x) {
b = x+2;
}
public String toString() {
return "a = " + a
+ " b = " + b;
}
}
Codice:
class B extends A
{
int b;
public B() {
b = a;
}
public String toString() {
return super.toString() + "\n"
+ "a = " + a + " b = " + b;
}
}
Codice:
public class Prova
{
public static void main(String[] args) {
B b = new B();
System.out.println(b.toString());
}
}
Per capire l'output prodotto dovresti seguire passo passo tutte le chiamate nel codice.
- istanzia un nuovo oggetto B.
- B estende A, quindi viene chiamato implicitamente il costruttore senza parametri di A.
Codice:
public A() {
this(++a);
}
- 'a' è un campo di classe statico, essendo di tipo 'int' il suo valore di default è inzializzato a 0 dalla virtual machine;
- nel costruttore di default di A il suo valore viene incrementato a 1 dall'operatore ++;
- quindi 'a' viene passato come parametro al costruttore di A che prende un parametro 'int' con la chiamata this(++a);
Codice:
public A(int x) {
b = x+2;
}
-
al campo 'b' della classe A viene assegnato il valore del parametro 'x' (che era 'a', valorizzata a 1) incrementato di 2;
- Ora abbiamo che 'a' vale 1 e il
campo 'b' della classe A vale 3;
- Si torna al contesto del costruttore della classe B;
Codice:
public B() {
b = a;
}
-
al campo 'b' della classe B (b oltre che in A è dichiarato anche in B, non viene ereditato, mentre il campo 'a' è visibile a B che lo eredita da A) viene assegnato il valore del campo 'a' (vale 1);
- Ora abbiamo che 'a' vale 1, il
campo 'b' della classe A vale 3 e il
campo 'b' della classe B vale 1;
- Si torna al contesto del metodo main;
Codice:
System.out.println(b.toString());
- viene invocato toString() della classe B;
Codice:
return super.toString() + "\n"
+ "a = " + a + " b = " + b;
- nel toString() di B per prima cosa viene invocato il toString() della classe che viene estesa da B, cioè A.
- nel toString() di A:
Codice:
return "a = " + a
+ " b = " + b;
- viene stampata la stringa "a = " a cui viene concatenato il valore di 'a', che come sappiamo, in questo momento vale 1;
- quindi alla precedente stringa viene concatenata la stringa " b = " a cui viene concatenato il valore
del campo 'b' di A che come sappiamo vale 3;
- si torna al contesto del toString() di B;
Codice:
return super.toString() + "\n"
+ "a = " + a + " b = " + b;
- qui, per farla breve, viene ristampato 'a' che vale sempre 1, e
il campo 'b' della classe B, che come abbiamo visto vale 1.
In pratica in questo esercizio era neccessario stare attenti alle regole di visibilità dei campi e all'ordine di inizializzazione delle varie parti di un'istanza di una classe che ne estende un'altra.