Newsgroup: it.comp.java
Titolo: Discussione logica sugli array di oggetti

Premetto che ho da poco iniziato a studiare il Java.
L'altro giorno ho avuto la necessita' di creare un array di oggetti
Label, cosě ho utilizzato la dichiarazione:
1) Label[] etichetta=new Label[10];
Eseguendo il programma, perň, mi veniva segnalato sempre un errore.
Dopo essermi scervellato a cercare di capire cosa poteva essere, ho
fatto una riflessione: in java la dichiarazione
2) Label etichetta
non crea un oggetto, ma un PUNTATORE all'oggetto ed e' per questo che
bisogna utilizzare la parola chiave new per allocare spazio per
l'oggetto stesso. Percio' la dichiarazione 1) usata da me
precedentemente, benche' sembrasse una dichiarazione di un array di
oggetti, era in realta' un' allocazione di memoria per contenere un
array di PUNTATORI ad oggetti (etichetta diviene un array di tipo
Label);
Percio', per risolvere il problema, ho inserito, ALL' INTERNO DEL
PROGRAMMA, un ciclo for che per ogni elemento [i] eseguiva:
3) erichetta[i] = new Label();
E cosě ha funzionato. Ora, quello che chiedo e' : il mio ragionamento
e' valido? Inoltre, č questo il modo giusto per creare un array di
oggetti? O esiste un modo piu' pulito (oltre alla classe Vector)?
Lo chiedo perchč questa soluzione mi sembra un po' "sporca",
probabilmente perche' vedo la parola chiave new strettamente legata
alle dichiarazioni e non alle "normali" istruzioni.
Grazie mille in anticipo per il vostro parere. :)
Bye a tutti, Animanera. :)
--
"La vanita' : decisamente il mio peccato preferito." - L' Avvocato del
Diavolo
email : 
anim...@mailroom.com
icq : 40379995
Nota : L' indirizzo sopra citato invia una copia della e-mail alla
casella 
drka...@wappi.com
 (che a volte non funziona e rispedisce il
msg al mittente:))
Sent via Deja.com 
http://www.deja.com/
Before you buy.

Provieni dalla programmazione C++, vero? 
I puntatori non sono presenti nel Java (al massimo si può parlare di
riferimenti, con comportamento simile ai reference del C++), inoltre gli
array vengono considerati come oggetti in tale linguaggio.
In Java  non sono presenti operatori come & per ottenere l'indirizzo di
memoria di una variabile o di un oggetto.
L'operatore new viene utilizzato sia per gli oggetti che per gli array
solamente perché entrambi (come già detto sopra) vengono valutati come
oggetti.
Una dichiarazione tipo:
Label[] etichetta;
non crea un puntatore ma solamente un variabile array di tipo Label non
ancora inizializzata, dato che non è ancora stato specificato quante
variabili del medesimo tipo dovrà contenere.
Per poter utilizzare un array occorre inizializzarlo specificando quante
variabili di quel determinato tipo deve contenere, es.
etichetta = new Label[10]; // crea un oggetto array che contiene dieci
variabili Label
O lo fai in questo modo (separando la dichiarazione dall'inizializzazione)
oppure in una sola istruzione come Label[] etichetta = new Label[10];.
Un terzo modo è quello di scrivere direttamente i valori da immettere,
come:
String [] array = { "ciao", "ciao", "ciao" };
Utilizzando questo sistema vengono create automaticamente +
variabili(secondo il numero di elementi messi all'interno di {}) atte a
contenere tali valori. 
Non so perché il compilatore ti segnala errore, (potresti riportarmi il
testo dell'errore?).
Cmq ogni volta che una variabile ha per tipo una classe viene identificata
come un riferimento agli oggetti di quella determinata classe.
Label etichetta = new Label();
etichetta = new Label("ciao");
Nella prima riga si dichiara la variabile etichetta che fa riferimento ad
un oggetto di tipo Label.
Nella seconda la variabile viene legata ad un altro oggetto Label, con la
conseguente rimozione automatica del primo oggetto.
Un caso che forse potrebbe aiutarti:
Label etichetta = new Label("ciao");
Label etichetta2 = etichetta;
qui abbiamo due variabili Label che fanno riferimento allo stesso oggetto
ed utilizzare etichetta o etichetta2 per farvi riferimento è indifferente.
Le poche differenze che potresti trovare con i reference del C++ è che non
si usa più il simbolo & postfisso al tipo per dichiarare un reference (dato
che vengono automaticamente implementati con le variabili che hanno come
tipo una classe) e che non possono essere utilizzati per far riferimento a
variabili di tipo primitivo, dato che non possono essere dichiarati con
tali tipi. 
Per il resto è uguale.
Spero di esserti stato di aiuto.

Sempre a proposito della precedente discussione volevo chiarire una
cosetta.
Io ho detto più volte che new Label[10]; era una dichiarazione di 10
variabili Label che venivano legate alla variabile array Label[] etichetta.
Alla fine del discorso volevo fare l'ultima parentesi che faccio adesso con
qualche aggiunta:
Label etichetta[] = new Label[10];
Io avevo detto che qua venivano create 10 variabili Label per contenere i
valori, non è proprio esatto, viene semplicemente creato un oggetto array
composto da dieci label 
e poi legato alla rispettiva variabile. Infatti io posso legare etichetta
ad un altro indice qualsiasi (utilizzando sempre l'operatore new o
appoggiandomi ad altri array).
Forse dovevo subito partire dicendo questo a proposito della discussione,
ma sono partito invece secondo la logica del C++, dove un array è solo un
nome che contiene + variabili omogenee. Credo che per un bel tempo mi
porterò dietro ciò che ho appreso con C++. 
Chiedo umilmente scusa.


Scusa, ma label non deve essere un oggetto. Devi far riferimento alla
classe. Il modo più semplice per rendersene conto è una dichiarazione del
tipo String[] st = new String[10]
st sarà istanza della classe String e sarà un array di oggetti tipo
String. Analogamente potrai scrivere Classe[] a = new Classe[10]; e poi
a[0] = new Class(parametri);
Spero ti sia stato utile!!
Ciao!

 Chiedo umilmente scusa.
No, hai fatto bene a spiegarmi il concetto in qusto modo perche' sono
proprio un ex-programmatore di C++!
Anche se ho capito la tua spiegazione (che poi era quello che pensavo
degli array di oggetti prima che mi uscisse l'errore) l'errore rimane.
Ho fatto un piccolo esempio che genera lo stesso errore:
APPLETJAVA:-------------------
import java.awt.Label;
import java.applet.*;
public class Errore extends Applet {
   Label[] etichetta=new Label[10];
public void init() {
   etichetta[0].setText("Prova");
   add(etichetta[0]);
}
}
FINE APPLET JAVA-------------------
FILE HTML CHE RICHIAMA L'APPLET:---------------
<html>
<body>
<APPLET CODE="Errore.class" WIDTH=200 HEIGHT=200>
</APPLET>
</body>
</html>
FINE FILE HTML CHE RICHIAMA L'APPLET----------
Prova a compilarlo semplicemente con "javac Errore.java" e a richiamare
l'appletviewer su Errore.htm.
L' applet non vera' eseguita e nella finestra del dos in cui avrai
richiamato l'appletviewer uscira':
java.lang.NullPointerException
        at Errore.init(Errore.java:10)
        at sun.applet.AppletPanel.run(AppletPanel.java:344)
        at java.lang.Thread.run(Thread.java:484)
Eseguendo un ciclo for del tipo:
for (i=0; i<10; i+)
   etichetta[i]=new Label();
prima di setText, l'errore si risolve.
Fammi sapere cosa ne pensi. :)
Grazie mille per la spiegazione. :)))
Bye, Animanera. :)


 prima di setText, l'errore si risolve.
Tutto questo é normale. L'istruzione
Label[] etichetta=new Label[10];
non ti crea un array riempito con 10 Label. Ti crea un array che *puo'*
contenere 10 oggetti Label, o piu' precisamente hai semplicemente creato
spazio in memoria per 10 referenze, inizializzate a null, che potranno piu'
tardi puntare su degli oggetti di tipo Label (quindi in realtà l'array non
"contiene" le Label, ma referenze verso oggetti Label).
Visto che l'array contiene delle reference null, allora é chiaro che se
tenti di chiamare un metodo utilizzando una tale referenza, nessun oggetto
puo' rispondere quindi ti lancia un NullPointerException.
Per farla breve, ecco la regola d'oro per creare un array inizializzato in
Java:
Label[] etichetta=new Label[10];
for (int i=0; i<etichetta.length; i++)
     etichetta[i]=new Label();
ma guarda, assomiglia a quello che hai fatto tu ;-)
bye
Carlo

Sono in ritardo.
Ma ogni elemento (o riferimento in questo caso) dell'array deve essere
inizializzato separatamente dagli altri.
Label [] array = new Label[10];
array[0] = new Label("ciao");
array[1] = new Label("string");
array[2] = new Label();
Mi permetto di rispondere con una domanda ad un'altra domanda. Ma perché il
compilatore segnala errore:
Color[] colore = new Color[10];
colore[1] = new Color(50,50,50);
?