En este módulo, exploraremos dos conceptos fundamentales en Haskell: Functor
y Foldable
. Ambos son clases de tipos que proporcionan abstracciones poderosas para trabajar con estructuras de datos de manera funcional.
Functor
¿Qué es un Functor?
Un Functor
es una clase de tipos que representa estructuras de datos que pueden ser mapeadas. En otras palabras, un Functor
es algo en lo que puedes aplicar una función a cada elemento dentro de la estructura sin cambiar la estructura en sí.
Definición de la Clase Functor
La clase Functor
se define en el módulo Prelude
de Haskell de la siguiente manera:
fmap
es una función que toma una función(a -> b)
y unFunctor
que contiene elementos de tipoa
(f a
), y devuelve unFunctor
que contiene elementos de tipob
(f b
).
Ejemplo de Functor: Lista
Las listas en Haskell son instancias de Functor
. Aquí hay un ejemplo de cómo usar fmap
con listas:
-- Definimos una función que incrementa un número en 1 increment :: Int -> Int increment x = x + 1 -- Usamos fmap para aplicar 'increment' a cada elemento de la lista result :: [Int] result = fmap increment [1, 2, 3, 4] -- El resultado será [2, 3, 4, 5]
Ejemplo de Functor: Maybe
El tipo Maybe
también es una instancia de Functor
:
-- Definimos una función que convierte un número a su representación en cadena toString :: Int -> String toString x = show x -- Usamos fmap para aplicar 'toString' a un valor de tipo Maybe resultMaybe :: Maybe String resultMaybe = fmap toString (Just 123) -- El resultado será Just "123"
Ejercicio Práctico
Ejercicio: Define una instancia de Functor
para un tipo de datos personalizado Box
.
data Box a = Box a deriving (Show) instance Functor Box where fmap f (Box x) = Box (f x) -- Prueba tu instancia de Functor main :: IO () main = do let box = Box 10 print $ fmap (*2) box -- Debería imprimir "Box 20"
Foldable
¿Qué es Foldable?
Foldable
es una clase de tipos que representa estructuras de datos que pueden ser "plegadas" (folded). Plegar una estructura de datos significa reducirla a un solo valor mediante la aplicación repetida de una función.
Definición de la Clase Foldable
La clase Foldable
se define en el módulo Prelude
de Haskell de la siguiente manera:
foldr
es una función que toma una función binaria(a -> b -> b)
, un valor inicial de tipob
, y una estructura de datos de tipot a
, y devuelve un valor de tipob
.
Ejemplo de Foldable: Lista
Las listas en Haskell son instancias de Foldable
. Aquí hay un ejemplo de cómo usar foldr
con listas:
-- Definimos una función que suma dos números add :: Int -> Int -> Int add x y = x + y -- Usamos foldr para sumar todos los elementos de la lista sumList :: [Int] -> Int sumList = foldr add 0 -- El resultado de sumList [1, 2, 3, 4] será 10
Ejemplo de Foldable: Maybe
El tipo Maybe
también es una instancia de Foldable
:
-- Usamos foldr para sumar el valor de un Maybe con un valor inicial sumMaybe :: Maybe Int -> Int sumMaybe = foldr (+) 0 -- El resultado de sumMaybe (Just 5) será 5 -- El resultado de sumMaybe Nothing será 0
Ejercicio Práctico
Ejercicio: Define una instancia de Foldable
para un tipo de datos personalizado Box
.
data Box a = Box a deriving (Show) instance Foldable Box where foldr f z (Box x) = f x z -- Prueba tu instancia de Foldable main :: IO () main = do let box = Box 10 print $ foldr (+) 5 box -- Debería imprimir "15"
Resumen
En esta sección, hemos aprendido sobre las clases de tipos Functor
y Foldable
en Haskell. Los Functor
nos permiten aplicar funciones a cada elemento dentro de una estructura de datos, mientras que los Foldable
nos permiten reducir una estructura de datos a un solo valor mediante la aplicación repetida de una función. Hemos visto ejemplos prácticos y ejercicios para reforzar estos conceptos.
En el próximo módulo, exploraremos el concepto de Mónadas, que es una extensión poderosa de los Functor
y Foldable
.
Curso de Programación en Haskell
Módulo 1: Introducción a Haskell
- ¿Qué es Haskell?
- Configuración del Entorno de Haskell
- Sintaxis Básica y Hola Mundo
- Haskell REPL (GHCi)