Come gestire i null quando si utilizza Java collection sort


Quando si utilizza la raccolta.ordina in Java cosa dovrei restituire quando uno degli oggetti interni è null

Esempio:

Collections.sort(list, new Comparator<MyBean>() {
    public int compare(MyBean o1, MyBean o2) {
      return o2.getDate().compareTo(o1.getDate());
     } 

});

Diciamo che o2 non è null ma o2.getDate() è, quindi dovrei restituire 1 o -1 o 0 aggiungendo una convalida null?

Author: Giancarlo Corzo, 2010-09-09

4 answers

Naturalmente, è una tua scelta. Qualunque sia la logica che scrivi, definirà le regole di ordinamento. Quindi "dovrebbe" non è davvero la parola giusta qui.

Se vuoi che null appaia prima di qualsiasi altro elemento, qualcosa del genere potrebbe fare

public int compare(MyBean o1, MyBean o2) {
    if (o1.getDate() == null) {
        return (o2.getDate() == null) ? 0 : -1;
    }
    if (o2.getDate() == null) {
        return 1;
    }
    return o2.getDate().compareTo(o1.getDate());
} 
 31
Author: Nikita Rybak, 2010-09-08 21:00:17

In Java 8 puoi anche usare nullsFirst():

Comparator.nullsFirst(Date::compareTo).compare(dateOne, dateTwo);

O nullsLast():

Comparator.nullsLast(Date::compareTo).compare(dateOne, dateTwo);

Questi metodi ordineranno null all'inizio o alla fine. Non c'è torto o ragione se consideri null più grande o più piccolo di un altro oggetto. Questo dipende totalmente da te, come altri hanno già affermato.

 15
Author: user1438038, 2016-07-22 16:03:29

Dipende, consideri null come un valore grande o un valore basso.

Puoi considerare la maggior parte delle volte che null

E 0 sarebbe un valore di ritorno terribile qui.

 2
Author: Colin Hebert, 2010-09-08 20:59:00

Seguendo la risposta di Nikita Rybak, ho già un comparatore enum e aggiungo solo la logica null da qui.

public enum Orden implements Comparator<CmunParametrosDTO> {
        ByStrDescripcion {
            public int compare(CmunParametrosDTO item1, CmunParametrosDTO item2) {
                if (item1.getStrDescripcion() == null && item2.getStrDescripcion() == null)
                    return 0;
                if (item1.getStrDescripcion() == null)
                    return 1;
                else if (item2.getStrDescripcion() == null)
                    return -1;
                return item1.getStrDescripcion().compareTo(item2.getStrDescripcion());
            }
        }
        public abstract int compare(CmunParametrosDTO item1, CmunParametrosDTO item2);

        public Comparator<CmunParametrosDTO> ascending() {
            return this;
        }

        public Comparator<CmunParametrosDTO> descending() {
            return Collections.reverseOrder(this);
        }
}

In questo modulo posso chiamare il metodo di ordinamento sulla mia lista.

    if(isBolOrdAscendente()) Collections.sort(listado, CmunParametrosDTO.Orden.ByStrDescripcion .ascending());
    else Collections.sort(listado, CmunParametrosDTO.Orden.ByStrDescripcion .descending());
 1
Author: ELD, 2013-01-10 23:40:19