Stream en Java explicado: Simplifica tu desarrollo ahora

| Última modificación: 18 de septiembre de 2024 | Tiempo de Lectura: 4 minutos

Algunos de nuestros reconocimientos:

Premios KeepCoding

Aunque no lo creas, hay una funcionalidad impresionante con la que puedes procesar colecciones de datos de manera eficiente. Estamos hablando de Stream en Java. Sí, ya sabemos que al inicio puede resultar un poco compleja de entender, sobre todo si has estado trabajando desde un enfoque tradicional con ArrayList, pero te aseguramos que con este post, aprenderás qué es un stream en Java, cómo funciona y, además, podrás ponerlo en práctica con un ejemplo sencillo.

qué es stream en Java

¿Qué es un stream en Java?

Si realmente quieres entender qué es un stream en Java, debes imaginar una tubería por la que pasan datos uno tras otro, y sobre esos datos lo que tú haces es aplicar distintas operaciones como: filtrarlos, transformarlos o combinarlos. El proceso es muy diferente de las listas o arrays tradicionales porque estos guardan los datos en memoria, mientras que los streams no almacenan nada.

Lo que sí hacen es procesar los datos directamente y de una forma mucho más eficiente. Algo muy ventajoso de los streams es que con ellos puedes enfocarte en qué quieres hacer con los datos sin tener que estar pensando en cómo recorrerás toda la colección de los mismos. De esta manera tu código es más limpio y fácil de leer.

Cómo funciona un stream en Java

El stream en Java opera teniendo en cuenta tres fases principales:

  1. Fuente de datos: Es la colección sobre la que se aplican las operaciones, como un List o Set.
  2. Operaciones intermedias: Filtrado, mapeo o transformación de los datos. Estas operaciones son “perezosas” (lazy), es decir, se ejecutan solo cuando se necesitan.
  3. Operación terminal: Finaliza el procesamiento, como collect(), findFirst(), o count().

Ejemplo práctico de stream en Java: Filtrando nombres de estudiantes

Vas a suponer que tienes una lista de nombres de estudiantes y deseas filtrar aquellos cuyos nombres tienen más de 5 letras. Para que no recorras la lista manualmente con un bucle, puedes usar un stream en Java y simplificar el código.

package com.arquitecturajava;

import java.util.ArrayList;
import java.util.List;

public class Principal {

public static void main(String[] args) {

List<String> estudiantes = new ArrayList<>();
estudiantes.add("Carlos");
estudiantes.add("Ana");
estudiantes.add("Sebastián");
estudiantes.add("Juan");
estudiantes.add("Laura");

// Creamos un stream para filtrar los nombres con más de 5 letras
List<String> estudiantesFiltrados = estudiantes.stream()
.filter(nombre -> nombre.length() > 5)
.toList();

// Mostramos los nombres filtrados
estudiantesFiltrados.forEach(System.out::println);
}
}

Lo que hicimos fue:

  • Crear una lista de nombres de estudiantes.
  • Usar un stream en Java para filtrar los nombres que tienen más de 5 letras mediante la operación filter.
  • Finalmente, los nombres filtrados se recogen en una nueva lista con la operación toList() y se imprimen en consola.

Debes tener cuidado porque el stream en java maneja una lógica compleja. Siempre recuerda que, a diferencia de los bucles tradicionales, los streams no recorren todos los elementos si no es necesario.

Como pudiste darte cuenta, en el ejemplo anterior, lo que hizo el stream fue filtrar los nombres uno por uno hasta encontrar todos los que cumplían con la condición de tener más de 5 letras.

Además, con el fin de mejorar el rendimiento y evitar procesamientos innecesarios, los streams evalúan de manera perezosa o lazy. De esta manera las operaciones intermedias solo se ejecutan cuando se necesita el resultado.

Streams y rendimiento

Te darás cuenta de que, con los streams en java también optimizarás el rendimiento. Por ejemplo, si usas la operación findFirst() en un stream, el procesamiento se detendrá inmediatamente al encontrar el primer elemento que cumpla con la condición. Así es como te ahorras tiempo de ejecución al trabajar con grandes volúmenes de datos.

Continuando con ejemplo anterior de la lista de estudiantes, ahora quieres encontrar el primer nombre que tenga más de 5 letras. Entonces, lo que haría el stream sería detenerse apenas encuentre el primer resultado que cumpla con esta especificación.

package com.arquitecturajava;

import java.util.ArrayList;
import java.util.List;

public class Principal2 {

public static void main(String[] args) {

List<String> estudiantes = new ArrayList<>();
estudiantes.add("Carlos");
estudiantes.add("Ana");
estudiantes.add("Sebastián");
estudiantes.add("Juan");
estudiantes.add("Laura");

// Filtrar y obtener el primer nombre con más de 5 letras
String primerNombre = estudiantes.stream()
.filter(nombre -> nombre.length() > 5)
.findFirst()
.orElse("No encontrado");

// Mostrar el resultado
System.out.println("Primer nombre: " + primerNombre);
}
}

Lo que ocurrió fue que, cuando el stream encontró el nombre de (Carlos), que era el que cumplía con la condición, detuvo la ejecución y no siguió evaluando los demás nombres. Como ves, no tuvo que recorrer el resto de la lista, porque no era necesario.

Stream vs. bucles tradicionales

Lo que sucede con los bucles tradicionales es que, como se manejan índices, variables de control y condiciones, aumenta el riesgo de que surjan errores. En cambio, los streams simplemente delegan la ejecución a varios hilos cuando usas parallelStream() y, por ende, se mejora el rendimiento en ciertas aplicaciones.

Ya tienes claro que los streams en Java te ofrecen una forma efectiva a la hora de trabajar con grandes volúmenes de datos. Recuerda que, al usarlos estarás aprovechando todas las capacidades modernas de Java, optimizarás tu desarrollo y mejorarás el rendimiento. Además, si estás interesado en dominar por completo esta y otras herramientas imprescindibles de Java, tenemos para ti el Bootcamp Java Full Stack creado por KeepCoding. Nosotros te brindaremos la oportunidad de entrar en el sector tecnológico donde la demanda de profesionales es alta y, por supuesto, los pagos son generosos. ¡Transforma tu carrera y cambia tu vida con este bootcamp intensivo!

Ramón Maldonado

Full Stack Developer y Responsable de Formación base en KeepCoding.

Posts más leídos

¡CONVOCATORIA ABIERTA!

Java y Spring Boot

Full Stack Bootcamp

Clases en Directo | Profesores en Activo | Temario 100% actualizado