Newsgroup: it.comp.java
Titolo: Recupero da una collection

salve a tutti, volevo sapere se con java 5 è possibile in qualche
modo ottenere gli oggetti contenuti in una collection senza
dover effettuare il casting.
s'intende che il problema ha senso solo quando le entry sono
oggetti appartenenti a classi differenti!
ho provato con la riflessione usando getMethods() di Class e
poi andando ad invocare il metodo sull'oggetto estratto tramite
invoke() di Method, ma è un bagno di sangue perchè bisogna
conoscere del metodo che si vuole utilizzare qual'è il suo indice 
all'interno dell'array di metodi che viene restituito da getMethods()
e poi confezionare un opportuno array di argomenti.
ciao e buon anno
giuseppe

 e poi confezionare un opportuno array di argomenti.
Ovvio. E' abbastanza complicato invocare dei metodi senza conoscere la 
classe di appartenenza e tantomeno gli argomenti necessari.
Spiegati meglio.


supponi di avere un Vector all'interno del quale metti
oggetti di varia natura.
Vector v = new Vector();
v.add("ciao");
v.add(new Integer(1));
Object ob0 = v.get(0);
Object ob1 = v.get(1);
ob0.toUpperCase();
ob1.intValue();
prova a vedere se ti funziona! in compilazione ti darà 2 errori
perchè toUpperCase() e intValue() non sono metodi di Object.
gli oggetti che tiro fuori dal vector sono di tipo Object, quindi
per eseguire le due ultime righe devo prima fare il casting
((String) ob0).toUpperCase();
((Integer) ob1).intValue();
quello che ho fatto io con la riflessione è stato di ottenere i
metodi di ogni oggetto estratto e quindi invocare quello che
interessa sull'oggetto.
Method[] met = ob0.getClass().getMethods();
Object args = new Object[0];
met[34].invoke(ob0, args); // supponendo che met[34] sia il metodo 
toUpperCase()
in questo modo non ho piu' il problema di fare casting, che peraltro
non potrei neanche ottenere se in fase di scrittura del codice
non ho idea dei tipi di oggetti che vengono archiviati.
sono consapevole che l'esempio è un po' sciocco, ma serve solo
per far capire cosa desidero fare. 

 toUpperCase()
Solo un piccolo suggerimento: Al posto dell'indice assoluto (Nel tuo
caso "34"), potresti usare il metodo
  getMethod(String name, Class[] parameterTypes)
passando come "name" il nome del metodo e come Class[] i parametri.
Oppure potresti usare "insanceof" per determinare il tipo di oggetto e
richiamare il metodo giusto:
  if (obj instanceof Integer) ((Integer)obj).intValue();
  elseif (obj instanceof String) ((String)obj).toUpperCase();
Ma mi pare che sia abbastanza costoso in termini di performance.
Una volta un saggio mi disse che se in un Vector hai oggetti molto
differenti tra di loro, allora sbagli qualcosa.
Cosa vorresti fare esattamente ?
-- 
Giambo - Occhio al filtro antispam _e_ alla whitelist !

 per far capire cosa desidero fare. 
Cosa succede se l'oggetto viene modificato e l'indice cambia ? Tutto il 
discorso va a donnine di facili costumi. Idem per quanto riguarda il 
nome del metodo (come ti hanno suggerito, al posto dell'indice), cosa 
succede se cambiano gli argomenti o se lo stesso metodo e' usato da due 
oggetti diversi ma con parametri e valori di ritorno differenti ?


in realtà nulla :) devo preparare una lezione sul java collection
framework e per la parte di esercitazione devo mostrare
l'inconveniente del downcasting quando si usano le collections.
pero' credo che oltre che un esercizio didattico potrebbe avere
concreta utilità. pensa ad un sistema di archiviazione remoto di
oggetti, tanti client si connettono ad un server e inviano un vector
di oggetti da archiviare, il server a secondo dei tipi di oggetti
ricevuti li memorizza nel repository nel modo piu' appropriato.
speravo che con java 5 qualcosa fosse stata fatta per risolvere
il problema.

 il problema.
Mai sentito parlare di interfacce ?

 il problema.
Mai sentito parlare di interfacce ?
seguita anche questa strada. una interfaccia con un singolo
metodo gestisci(Object ob) che viene poi implementata
in tante classi quante sono i tipi di oggetti che voglio gestire.
ma il casting alla fine lo fai! lo sposti solo dentro la classe che
va a gestire quel tipo di oggetto; ed in ogni caso è necessaria
una sfilza di
if(entry instanceof ...)
a meno che non intendevi dire altro... 

 if(entry instanceof ...)
Santo cielo, ma qui siamo all'apice del ridicolo. Come puoi insegnare 
Java quando non conosci nemmeno i principi basilari della programmazione 
ad oggetti ? Nessuno ti hai mai detto che chi usa un oggetto non deve 
sapere come l'oggetto funziona ? Secondo te per quale motivo esistono le 
interfacce ?
 > a meno che non intendevi dire altro...
Ovviamente intendevo altro, studiati le interfacce e come si usano, poi 
magari ne riparliamo.
Spero solo che a nessuno dei tuoi studenti venga in mente di cercare il 
tuo nome nei newsgroup...

 il problema.
Non e' affatto un problema, semplicemente "non esiste".


 facciamo simulazioni didattiche.
I pezzi di carta non sono sinonimo di conoscenza ed e' evidente che tu
il Java lo conosci come io conosco la meccanica quantistica.
perchè sei così inviperito? non mi sono mai vantato di essere
un genio di java. io non devo diventare un insegnante di java,
java è solo una delle tantissime cose che devo conoscere per
potere insegnare.
nessuno nasce con la scienza infusa, vengo qui per
documentarmi e crescere non per sputare veleno come sembri
fare tu.

 fare tu.
Veramente per documentarsi sarebbe molto piu' utile acquistare qualche 
libro che tratti la programmazione in Java o, meglio ancora nel tuo 
caso, la programmazione ad oggetti, visto che hai gravi lacune in questo 
senso.

 fare tu.
Veramente per documentarsi sarebbe molto piu' utile acquistare qualche
libro che tratti la programmazione in Java o, meglio ancora nel tuo
caso, la programmazione ad oggetti, visto che hai gravi lacune in questo
senso.
ma sulla base di cosa ti sei autoproclamato censore del newsgroup?
ora sei tu che stabilisci cosa si puo' chiedere e cosa no sul NG?
se non ti andava di rispondere, nessuno ti obbligava a farlo!
contrariamente a quello che pensi, ritengo di conoscere la
programmazione ad oggetti, dubito che altrimenti mi avrebbero
fatto laureare e neppure mi avrebbero fatto entrare in una
scuola di specializzazione post-universitaria a numero chiuso
dove entrano 20 persone a fronte di oltre 200 aspiranti.
e giusto per completare il quadretto, ti voglio confidare che
software (in java) per la cui stesura sono stato tra le colonne
portanti, sono usati in grosse aziende, tra cui uno dei principali
operatori di telefonia mobile.
chissà, magari di programmazione ad oggetti ne so qualcosina
piu' di te!
mi sa che sei un tantinello frustrato e cerchi l'occasione per
scaricare su qualcuno la tua rabbiosità!
adieux

 scaricare su qualcuno la tua rabbiosità!
Si si certo... hai anche una laurea in psicologia adesso ?

 programmazione ad oggetti,
Dalle domande, non è così.
Leggi Thinking in Java (lo cerchi su google, è gratis).

In Java 5, forse anche nelle versioni precedenti si possono usare 
concetti di generic Programming.
Che permettono di non dover fare il cast degli oggetti quando si 
recuperano da un collection.
Basta vedere come é scritta la classe ArrayList.

Rispondo qui ma ho letto tutti il 3d...
Penso tu abbia le idee o non molto chiare o troppo accademiche ( è una
critica costruttiva!)
Dalla mia esperienza di analista (e quindi IMHO) ti propongo una riflessione
sulle collections che magari potrebbe servirti in generale.
Le collection sono implementazioni general purpose di strutture dati, quindi
sono state progettate per perseguire tale scopo.
Ciò non significa che le collections siano classi "intelligenti" ossia che
ti facciano tutti i cast di cui hai bisogno (il che è impossibile per ovvi
motivi!), anzi, essendo strutture dati, giustamente hanno responsabilità
*solo sull'organizzazione dei dati e non sui dati stessi*. In altre parole
non mi attenderei che una collection "sapesse" che dato ospita se non che
per ordinare i dati in essa contenuti, ed anche in tal caso la dipendenza è
solo verso l'interfaccia Comparable ( vedi anche Comparator) quindi non è
una dipendenza verso i dati. L'operazione di casting, pertanto,  non è da
ritenere un problema...in poche parole, chi usa la collection
ha la responsabilità su ciò che gli inserisce/estrae da essa, e quindi
*conosce* cosa inserisce/estrae...il problema della reflection è accessorio,
ad esempio,
nelle applicazioni reali si progettando classi wrapper (o per estensione)
che "specializzano" le collections rispetto ai dati
che conterranno, mediante metodi del tipo
Impiegato getImpiegato(...)
Operaio getOperaio(...)
e quindi restituiscono riferimenti di tipo opportuno, svincolando l'utente
dei dati dall'accesso ai dati e quindi concentrando la logica di accesso (
compreso il casting) in una sola classe interfaccia... puoi notare come le
responsabilità di cui ti ho detto prima siano concentrate proprio in questa
classe "wrapper"...
la solita storia OO; il binomio  Interfaccia / responsabilità ...
Comunque sia, visto cha hai sviluppato progetti commerciali, queste cose già
le sai (sono un po' prolisso per natura).
Se il tuo problema è quello di fare un esempio concreto che mostri come le
collection possano contenere dati non omogenei,
allora  potresti fare un esempio del tipo "coda di utenti", ossia definire
una gerarchia di classi utente del tipo Impiegato, CapoUfficio, Operaio,
Manager
(piuttosto che usare String, Integer etc) e gestirne le comunicazioni
dirette verso di loro da parte di un Centralino ed una SegreteriaTelefonica.
Spero di esserti stato d'aiuto.
Luciano


grazie. sei stato gentilissimo.
in effetti alla fine chiedevo se c'era qualche novità con java 5,
e poi ho scoperto che qualcosa di nuovo c'è, con
l'introduzione dei generici, che se da un lato vincolano
all'inserimento di oggetti della stessa natura, però
permettono di recuparare le entry senza bisogno del casting e
anzi con l'unboxing si puo' recuperare direttamente all'interno
di variabili di tipo primitivo.
ho aggiunto pure un'esercitazione su questa novità e cosi'
penso che l'argomento "collections & co" sia esaustivamente
trattato per una lezione che teoricamente è indirizzata a
ragazzi delle superiori :)
giuseppe

 ragazzi delle superiori :)
bene. Alla prossima.