Empresas
Empleos
  • Sobre nosotros
  • Soluciones
    • Publicación de vacantes
      Publica tu vacante y recibe candidatos calificados en 48h.
    • Evaluación de candidatos
      500+ pruebas técnicas y psicológicas, más anti-fraude.
    • Headhunting
      Búsqueda ejecutiva a la medida de principio a fin.
    • Nómina + EOR
      Dispersión de nómina y EOR en más de 15 países de LATAM.
  • Precios
  • Empleos

0

317
Vistas
Ordenar la lista por múltiples campos y múltiples criterios

Tengo el siguiente código:

 list.sort(Comparator .comparing(ProgrammData::getEnd) .thenComparing(ProgrammData::getStart).reversed());

Mi problema es que quiero tener mi lista ordenada por varias cosas: 1.) Agruparlos en eventos futuros y eventos pasados (verificando si System.currentMilliseconds() es más grande que la marca de tiempo final) 2.) Ordenar eventos futuros por empezar ascendiendo 3.) Ordenar eventos pasados por fin descendiendo

¿Puedo hacer esto con Java 8 Lambda o necesito otra forma de clasificar los elementos?

Ejemplo:

 events could look like this: name, start, end event1, 2022-02-220100, 2022-02-220300 event2, 2022-02-220200, 2022-02-241800 event3, 2022-02-251200, 2022-02-281500 event4, 2022-02-261600, 2022-02-262100 if now() is 2022-02-221200 So the order should be: event3 (next item in the future) event4 (2nd next item in the future) event2 (Ended closer to now than event1) event1 (Longest in the past)
over 4 years ago · Santiago Trujillo
4 Respuestas
Responde la pregunta

0

Prueba esto :

 final long currentTime = System.currentTimeMillis(); list.sort((el1, el2) -> { if (el1.equals(el2)) { return 0; } boolean isEl1Future = el1.getEnd().getTime() > currentTime; boolean isEl2Future = el2.getEnd().getTime() > currentTime; if (isEl1Future != isEl2Future) { return isEl1Future ? -1 : 1; } if (Boolean.TRUE.equals(isEl1Future)) { return el1.getStart().before(el2.getStart()) ? -1 : 1; } return el1.getEnd().after(el2.getEnd()) ? -1 : 1; });
over 4 years ago · Santiago Trujillo Denunciar

0

Hay varias cosas para notar. Primero, uno es el .thenComparing(...) , que solo tiene lugar si los resultados de la comparación anterior son iguales. Puede leer más sobre su comportamiento en los documentos .

En segundo lugar, si yo fuera usted, no me molestaría en abusar del flujo si pudiera resolverlo con un simple comparador. Suponiendo que está buscando una nueva instancia de la lista ProgrammData , escribí mi código en estilo de transmisión, pero el Comparator se puede usar con el método de sort de List .

 private List<ProgrammData> sortedProgramms(List<ProgrammData> dataList) { final LocalDateTime now = LocalDateTime.now(); return dataList.stream() .sorted((e1, e2) -> { if (e1.getStart().isAfter(now) && e2.getStart().isAfter(now)) { return e1.getStart().compareTo(e2.getStart()); } return e2.getEnd().compareTo(e1.getEnd()); }) .collect(Collectors.toList()); }

LocalDateTime().now() está usando System.currentTimeMillis() adentro, si no hay un reloj dado más preciso.

over 4 years ago · Santiago Trujillo Denunciar

0

Debe dividir los eventos pasados y futuros en diferentes listas y ordenarlos en consecuencia. El paso final es unirse a ambas listas.

 public static void main(String[] args) { ProgrammData programmData1 = new ProgrammData("a", LocalDateTime.now().plusDays(1), LocalDateTime.now().plusDays(1)); ProgrammData programmData2 = new ProgrammData("b", LocalDateTime.now().plusDays(2), LocalDateTime.now().plusDays(2)); ProgrammData programmData3 = new ProgrammData("c", LocalDateTime.now().minusDays(1), LocalDateTime.now().minusDays(1)); ProgrammData programmData4 = new ProgrammData("c", LocalDateTime.now().minusDays(2), LocalDateTime.now().minusDays(2)); List<ProgrammData> programmDataList = new ArrayList<>(); programmDataList.add(programmData1); programmDataList.add(programmData2); programmDataList.add(programmData3); programmDataList.add(programmData4); final List<ProgrammData> collect = programmDataList.stream().sorted(Comparator .comparing(ProgrammData::end)).toList(); LocalDateTime localDateTime = LocalDateTime.now(); final List<ProgrammData> pastEvents = collect.stream().filter(pd -> pd.end.isBefore(localDateTime)) .sorted(Comparator .comparing(ProgrammData::end).reversed()).toList(); final List<ProgrammData> futureEvents = collect.stream().filter(pd -> pd.end.isAfter(localDateTime)).toList(); List<ProgrammData> sortedListAsRequired = new ArrayList<>(); sortedListAsRequired.addAll(futureEvents); sortedListAsRequired.addAll(pastEvents); System.out.println(sortedListAsRequired); } static record ProgrammData(String name, LocalDateTime start, LocalDateTime end) { }

El resultado es algo como esto:

 [ProgrammData[name=a, start=2022-02-23T18:08:59.564300200, end=2022-02-23T18:08:59.568806900], ProgrammData[name=b, start=2022-02-24T18:08:59.568806900, end=2022-02-24T18:08:59.568806900], ProgrammData[name=c, start=2022-02-21T18:08:59.568806900, end=2022-02-21T18:08:59.568806900], ProgrammData[name=c, start=2022-02-20T18:08:59.568806900, end=2022-02-20T18:08:59.568806900]]
over 4 years ago · Santiago Trujillo Denunciar

0

Tu ejemplo es confuso. Como indica en el encabezado, event2 debe manejarse como si fuera en el futuro, debido a que su hora de finalización ( 2022-02-241800 ) es posterior a ahora ( 2022-02-221200 ), por lo que los elementos ordenados deben ser

 event2 event3 event4 event1

Si eso es correcto, podría intentar algo como lo siguiente:

 events.sort((e1, e2) -> { // -1: e1 and e2 in the past // 0: e1 and e2 in distinct periods // +1: e1 and e2 in the future int period = Integer.signum( Integer.signum(e1.getEnd().compareTo(now)) + Integer.signum(e2.getEnd().compareTo(now)) ); if (period == 0) { return -e1.getEnd().compareTo(now); } // > 0: e1 is after e2 // = 0: e1 is equal to e2 // < 0: e1 is before e2 int comparation = e1.getComparingDateTime(now).compareTo( e2.getComparingDateTime(now) ); return period * comparation; });

Dado

 class ProgramData { ... public LocalDateTime getComparingDateTime(LocalDateTime reference) { if (reference.isAfter(end)) { // Past return end; } // Future return start; } ... }
over 4 years ago · Santiago Trujillo Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Comercial
Legal
Términos y condiciones Política de privacidad
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomiéndame algunas ofertas
Necesito ayuda