La programación funcional no es apátrida; más bien, la programación funcional le proporciona formas de controlar el estado.
Además, el “estado” en la “máquina de estados” está completamente divorciado del estado a nivel de lenguaje. ¡Las máquinas de estado a menudo se definen puramente en términos de funciones matemáticas sin ninguna referencia al estado mutable en absoluto! No solo podemos representar una máquina de estado en un lenguaje funcional, sino que la representación en realidad se parece más a cómo hablaríamos de máquinas de estado a un alto nivel.
Por ejemplo, un autómata determinista de estado finito (DFA) generalmente se define en términos de un par de conjuntos (los estados [matemáticas] Q [/ matemáticas] y el alfabeto [matemáticas] \ Sigma [/ matemáticas]), el comienzo [matemáticas ] s [/ math] y acepta estados y una función de transición. Podemos representar esto con bastante fidelidad en Haskell, utilizando tipos en lugar de los conjuntos:
- ¿Crees que es posible conseguir un trabajo en Google como ingeniero químico?
- ¿Cuál es la mejor y más rápida forma de obtener una tarjeta verde con una licenciatura en ciencias de la computación (ingeniería de software)?
- ¿Cuáles son algunos trabajos de gestión de proyectos de software que se pueden realizar de forma remota?
- ¿Cuál es el mejor software para limpiar el sistema y aumentar el rendimiento?
- ¿Cuáles son sus actividades diarias como ingeniero de DevOps en su proyecto actual?
datos DFA qs = DFA {
inicio :: q,
aceptar :: [q],
paso :: q -> s -> q
}
El DFA se ejecuta aplicándolo a una cadena de elementos desde s
(es decir, [s]
) y verificando si el estado resultante es uno de los estados aceptados. De hecho, esto es solo un pliegue:
– | ¿El DFA dado acepta la cadena dada?
ejecutar DFA {start, accept, step} string = foldl step start string `elem` accept
Entonces podríamos usar esta definición para DFA específicos especificando los tipos correctos para los estados y el alfabeto y proporcionando los tres campos. El artículo de Wikipedia tiene una máquina de ejemplo que combina múltiplos de 3 en binario:
El alfabeto es cadenas de dos símbolos y tenemos tres estados:
datos Σ = A | B derivando la ecuación
datos Q = S₀ | S₁ | S₂ derivando la ecuación
(Me gusta usar Unicode pero, por supuesto, no es necesario).
La función de paso es natural para escribir con coincidencia de patrones:
paso ‘S₀ A = S₀
paso ‘S₀ B = S₁
paso ‘S₁ A = S₂
paso ‘S₁ B = S₀
paso ‘S₂ A = S₁
paso ‘S₂ B = S₂
Finalmente, podemos poner todo junto:
wikiDFA = DFA {
inicio = S₀,
aceptar = [S₀],
paso = paso ‘
}
Ahora podemos usar esto para verificar cadenas en nuestro formato:
* Principal> ejecutar wikiDFA [B, A, B, A, B, A]
Cierto
* Principal> ejecutar wikiDFA [B, A, B, A, B, B]
Falso
¡Así que implementar claramente un DFA es poco más que transcribir la notación normal en una sintaxis ligeramente diferente!
Por supuesto, en la práctica, hay muchas razones diferentes para implementar una máquina de estado, por lo que no siempre querrá usar este método en particular, ya sea por razones de legibilidad o rendimiento. Y los lenguajes funcionales admiten todas estas otras formas, incluido el uso del estado mutable real. Lo importante de mi respuesta no son los detalles específicos de lo que hice, sino el hecho de que no solo es posible sino también simple y natural .