La programación funcional (FP) es un paradigma de desarrollo que trata la computación como la evaluación de funciones matemáticas y evita cambiar el estado o los datos mutables. En JavaScript, este enfoque puede ayudarte a escribir código más limpio, reutilizable y fácil de probar.
¿Qué es la Programación Funcional?
La programación funcional se basa en varios principios clave:
- Funciones puras: funciones que no tienen efectos secundarios y siempre devuelven el mismo resultado para los mismos argumentos.
- Inmutabilidad: los datos no cambian. En lugar de modificar una estructura de datos, se crea una nueva.
- Funciones de primera clase y orden superior: las funciones pueden ser tratadas como valores, pasadas como argumentos y devueltas por otras funciones.
- Composición: construir funciones complejas a partir de funciones simples.
1. Funciones Puras
Una función pura siempre entrega el mismo resultado con los mismos parámetros y no produce efectos colaterales (como modificar una variable externa o escribir en un archivo).
// Función pura
const sumar = (a, b) => a + b;
console.log(sumar(2, 3)); // 5
console.log(sumar(2, 3)); // 5, siempre el mismo resultado
Una función impura sería:
let total = 0;
function sumarImpuro(a) {
total += a; // Modifica una variable externa
return total;
}
2. Inmutabilidad
En programación funcional, los datos son inmutables. Eso significa que en vez de modificar un objeto o arreglo, creas uno nuevo.
const original = [1, 2, 3];
const nuevo = [...original, 4];
console.log(original); // [1, 2, 3]
console.log(nuevo); // [1, 2, 3, 4]
Para objetos:
const persona = { nombre: "Ana", edad: 25 };
const personaNueva = { ...persona, edad: 26 };
console.log(persona); // { nombre: "Ana", edad: 25 }
console.log(personaNueva); // { nombre: "Ana", edad: 26 }
3. Funciones de Orden Superior
Una función de orden superior recibe una función como argumento o devuelve una función.
const saludar = (nombre) => `Hola, ${nombre}`;
const procesar = (callback, nombre) => callback(nombre);
console.log(procesar(saludar, "Luis")); // "Hola, Luis"
Otro ejemplo con arrays:
const numeros = [1, 2, 3, 4, 5];
const pares = numeros.filter((n) => n % 2 === 0); // [2, 4]
const cuadrados = numeros.map((n) => n * n); // [1, 4, 9, 16, 25]
const suma = numeros.reduce((acc, n) => acc + n, 0); // 15
4. Composición de Funciones
La composición permite combinar funciones simples para construir lógica compleja de forma legible.
const agregarUno = (x) => x + 1;
const duplicar = (x) => x * 2;
// Composición manual
const procesar = (x) => duplicar(agregarUno(x));
console.log(procesar(3)); // (3 + 1) * 2 = 8
Con librerías como lodash/fp
o Ramda
:
// usando lodash/fp
import { flow } from "lodash/fp";
const procesar = flow(agregarUno, duplicar);
console.log(procesar(3)); // 8
5. Aplicación práctica: Filtrar y transformar datos
Caso real: tienes una lista de productos. Quieres aplicar un descuento del 10% solo a los que están disponibles y calcular el total.
const productos = [
{ nombre: "Laptop", precio: 1000, disponible: true },
{ nombre: "Tablet", precio: 500, disponible: false },
{ nombre: "Monitor", precio: 300, disponible: true },
];
const totalConDescuento = productos
.filter((p) => p.disponible)
.map((p) => ({ ...p, precio: p.precio * 0.9 }))
.reduce((acc, p) => acc + p.precio, 0);
console.log(`Total a pagar: $${totalConDescuento}`); // Total a pagar: $1170
6. Ventajas de la Programación Funcional
✅ Código más predecible y fácil de probar
✅ Favorece la reutilización y la composición
✅ Reduce errores derivados de efectos colaterales
✅ Ideal para entornos asincrónicos y programación reactiva
7. Herramientas y Librerías Funcionales
- Ramda: Utilidades para FP puras.
- Lodash/fp: Variante funcional de Lodash.
- RxJS: Programación reactiva y observables.
¿Qué sigue?
La programación funcional te permite crear código más robusto y fácil de mantener. Dominar funciones puras, composición y trabajar con datos inmutables te prepara para desafíos complejos del desarrollo moderno.
Puedes dar el siguiente paso aprendiendo sobre currying, memoization, o monads en JavaScript.