Ma voi le wrappate le liste?

Posted by Paolo Dona' Wed, 06 Dec 2006 07:45:00 GMT

Ciao, in un progetto su cui sto lavorando sto provando un approccio che non avevo mai usato in passato per le liste di oggetti java, immaginate che di avere una lista tipo:

List<SomeObject> list = new ArrayList<SomeObject>();

Se volessi estrarre dalla lista tutti gli elementi aventi un certo campo valorizzato ad un dato valore, ovvero fare un filtro, farei:

class SomeObject {
  public static List<SomeObject> filterByField(List<SomeObject> input, String value) {
    // ciclo la lista input e restituisco una lista nuova con gli oggetti che hanno field=value 
  }
}

usato così:

List<SomeObject> all = new ArrayList<SomeObject>();
List<SomeObject> filtered = SomeObject.filterByField(all, "someValue");

Il fatto però di avere metodi statici ‘helper’ dentro SomeObject per aggiungere funzionalità ad una lista non mi piace molto… ho provato invece a wrappare List e a spostare il metodo filerByValue da SomeObject alla nuova classe SomeObjects:

class SomeObjects extends ArrayList<SomeObject> {
   public SomeObjects filterByField(String value){
     // filtro ciclando gli elementi in this e restituisco una nuova istanza di SomeObjects
   }
}
Il codice di utilizzo quindi diventa:
SomeObjects all = new SomeObjects();
SomeObjects filtered = all.filterByField("someValue");

Che mi pare molto più pulito e leggible, che ve ne pare?

So che non è un gran cambiamento, ma ho un parametro in meno per ogni filterByXXX che desidero aggiungere e ogni metodo è nel posto che gli compete, ovvero i medoti per filtrare una lista stanno nella lista e non come metodi helper dell’oggetto contenuto.

Un’altro punto dove questo approccio è utile è nei Dao che wrappano funzionalità di IBatis o Hibernate, dove si trova spesso codice di questo tipo per prevenire il ritorno di liste nulle:

List<SomeObject> result = new ArrayList<SomeObject>();
result.addAll( ...queryForList("your query", param));
return result;

Con i wrapper possiamo scrivere un costruttore ad hoc, che prende una lista in input e fa addAll(...) solo se è diversa da null:

public class SomeObjects extends ArrayList<SomeObject> {

    public SomeObjects () {}

    public SomeObjects (Collection<SomeObject> c) {
       if (c!=null) addAll(c);
    }
}

E il codice di utilizzo diventa magicamente:

return new SomeObjects(...queryForList("your query", param));

Fatemi sapere che ne pensate, io mi sto trovando bene con questo approccio.

_ Paolo Donà si occupa di sviluppo web in Java e Ruby, sviluppo progetti su commessa e formazione/training. Potete contattarlo via mail o leggere il suo blog aziendale o personale. _

Posted in  | Tags  | 8 comments | no trackbacks

Comments

  1. Avatar Lucio Benfante said about 7 hours later:

    Ciao, il meccanismo è interessante, e sicuramente il codice di utilizzo è molto più leggibile e semplice da scrivere.

    Rimane però la necessità di implementare n classi diverse…che in gran parte faranno la stessa cosa. Sei passato da n metodi di ricerca a n estesioni di List per aggiungere il metodo di ricerca. (ovvio non è detto che si possa estendere solo per i metodi di ricerca)

    Fatalità oggi mi sta succedendo proprio questo: avrò implementato almeno 5 volte un metodo per fare una ricerca sequenziale su una List (di tipi diversi), praticamente sempre confrontando per uguaglianza un singolo campo.

    Estendere una list non avrebbe migliorato di molto il mio lavoro. Un approccio “più classico”, operante non per ereditarietà secondo me sarebbe più flessibile.

    MyObject o = ListUtils.findSequential(
        myList, new Comparator() {...});

    In generale secondo me è poco utile legarsi così strettamente al tipo contenuto all’interno della collezione.

  2. Avatar enrico said 1 day later:

    Personalmente, ho sempre fatto così, avrei messo il/i metodo static per filtrare, in una classe esterna di utility tipo UtilityFilter. Quindi sono più in sintonia con quanto proposto da Lucio.

  3. Avatar Leola33Boone said 1840 days later:

    People deserve good life time and loans or student loan will make it better. Just because people’s freedom relies on money.

  4. Avatar Louella19JOHNSON said 2278 days later:

    Are you still looking for professional writing services? Quit your search, visit home page and buy papers and you will never be sorry.

  5. Avatar Lincoln said 2322 days later:

    Thank you for sharing your thoughts. I really appreciate your efforts and I will be waiting for your further write ups thanks once again.

  6. Avatar ramandeep kaur dhillon MTV Roadies X Video said 2323 days later:

    Actually no matter if someone doesn’t be aware of after that its up to other viewers that they will help, so here it occurs.

  7. Avatar geebranz said 5420 days later:

    Amazing mechanism

    Holiday Season

  8. Avatar baby photography said 5421 days later:

    Cant believe this article made soo much sense now. You really have a talent for this! Continue pressing on!

Trackbacks

Use the following link to trackback from your own site:
http://www.jugpadova.it/articles/trackback/10900

(leave url/email »)

   Comment Markup Help Preview comment