1. Información general
La API Java Stream fue la característica principal de la versión Java 8. Los flujos representan secuencias de objetos evaluadas de forma perezosa y proporcionan una API rica, fluida y monádica.
En este artículo, veremos rápidamente las formas de obtener el último elemento de una secuencia. Tenga en cuenta que debido a la naturaleza de los arroyos, no es una operación natural . Asegúrese siempre de no trabajar con transmisiones infinitas .
2. Usando la API Reducir
Reducir , en pocas palabras, reduce el conjunto de elementos de una secuencia a un solo elemento.
En este caso, reduciremos el conjunto de elementos para obtener el último elemento en la secuencia. Tenga en cuenta que este método solo devolverá resultados deterministas para Streams secuenciales .
Usemos una lista de valores de cadena , obtengamos el flujo de la lista y luego reduzcamos:
List valueList = new ArrayList(); valueList.add("Joe"); valueList.add("John"); valueList.add("Sean"); Stream stream = valueList.stream(); stream.reduce((first, second) -> second) .orElse(null);
Aquí, la corriente se reduce a un nivel en el que se deja solo con el último elemento. Si la secuencia está vacía, devolverá un valor nulo .
2. Uso de la función de omisión
La otra forma de obtener el último elemento de la secuencia es omitiendo todos los elementos anteriores . Esto se puede lograr utilizando la función Omitir de la clase Stream . Tenga en cuenta que, en este caso, estamos consumiendo Stream dos veces, por lo que hay un impacto claro en el rendimiento .
Creemos una lista de valores de cadena y usemos su función de tamaño para determinar cuántos elementos omitir para llegar al último elemento.
Aquí está el código de ejemplo que obtiene el último elemento usando skip :
List valueList = new ArrayList(); valueList.add("Joe"); valueList.add("John"); valueList.add("Sean"); long count = valueList.stream().count(); Stream stream = valueList.stream(); stream.skip(count - 1).findFirst().get();
“Sean” termina siendo el último elemento.
4. Obtener el último elemento de una corriente infinita
Tratar de obtener el último elemento del flujo infinito conduciría a una secuencia infinita de evaluación realizada en elementos infinitos. Tanto skip como reduce no volverán de la ejecución de la evaluación a menos que limitemos el flujo infinito a un número específico de elementos usando la operación de límite .
Aquí está el código de ejemplo donde tomamos una secuencia infinita e intentamos obtener el último elemento:
Stream stream = Stream.iterate(0, i -> i + 1); stream.reduce((first, second) -> second).orElse(null);
En consecuencia, el flujo no regresará de la evaluación y terminará deteniendo la ejecución del programa .
5. Conclusión
Vimos diferentes maneras de conseguir el último elemento de una corriente tanto usando reducir y Skip API. También analizamos por qué esto no es posible con flujos infinitos.
Vimos que obtener el último elemento de una secuencia no es fácil en comparación con obtenerlo de otras estructuras de datos. Esto se debe a la naturaleza perezosa de los flujos que no se evalúan a menos que se invoque la función terminal y nunca sabemos si el elemento evaluado actualmente es el último.
Los fragmentos de código se pueden encontrar en GitHub.