- Flix es un lenguaje orientado a efectos desarrollado por Aarhus University y la comunidad de código abierto, que combina programación funcional, imperativa y lógica en un solo lenguaje
- Su núcleo es un sistema de efectos que trata los efectos secundarios a nivel de tipos, y aumenta la modularidad y la capacidad de razonamiento mediante seguimiento de pureza, efectos definidos por el usuario, handlers y reanudaciones múltiples
- La superficie del lenguaje es amplia: tipos de datos algebraicos, pattern matching, registros extensibles, traits, tipos de kind de orden superior, tipos y efectos asociados, concurrencia estructurada, interoperabilidad con Java y Datalog integrado
- La biblioteca estándar ofrece más de 3,100 funciones y, mediante Maven, también permite acceder al ecosistema Java, por lo que apunta a un alcance de uso que no se limita a un lenguaje de investigación
- El compilador apunta a bytecode de JVM y tiene una arquitectura paralela e incremental; destaca mejoras de velocidad de 5x–7x en una máquina de 24 núcleos y un rendimiento de 60,159 líneas/segundo con Apple M2 Pro/OpenJDK 21
La dirección del lenguaje Flix
- Flix es un lenguaje orientado a efectos basado en principios que combina programación funcional, imperativa y lógica
- Lo desarrollan Aarhus University y una comunidad de contribuidores de código abierto
- El sistema de efectos es un eje central de este lenguaje de tipos estáticos: modela explícitamente los efectos secundarios y ayuda a la modularidad y al razonamiento sobre programas
- Mediante efectos definidos por el usuario y handlers, los programadores pueden implementar sus propias estructuras de control
- Flix destaca, entre los lenguajes orientados a efectos, por una implementación madura, una biblioteca estándar amplia, documentación detallada y soporte de herramientas
Tipos, pureza y sistema de efectos
- Flix soporta tipos de datos algebraicos, un elemento básico de la programación funcional, y pattern matching
- Incluye soporte integrado para tuplas y registros; los registros usan tipado estructural y son extensibles
- El compilador rastrea con precisión la pureza de todas las expresiones dentro del programa
- Si una expresión es pura, ofrece la garantía de que no tiene efectos secundarios y es referencialmente transparente
- También rastrea la pureza en funciones de orden superior mediante polimorfismo de efectos
- Por ejemplo, la pureza de
List.mapdepende de la pureza de la funciónfque recibe como argumento
- Por ejemplo, la pureza de
- Los efectos algebraicos habilitan efectos definidos por el usuario y handlers
- Flix soporta especialmente multi-shot resumptions
- Los handlers de efectos se usan para mejorar el razonamiento sobre programas, la modularidad y la capacidad de prueba
Cambios basados en regiones y reflexión de pureza
- Flix soporta cambios locales basados en regiones, lo que permite usar internamente estado mutable y operaciones destructivas mientras hacia afuera se muestra como una función pura
- Es adecuado para funciones que se escriben de forma más natural con datos mutables, o para casos en los que las estructuras de datos mutables son más eficientes, como los algoritmos de ordenamiento
- La reflexión de pureza es una estructura de metaprogramación en la que una función de orden superior inspecciona la pureza de sus argumentos funcionales y cambia su comportamiento según esa información
DelayList.mapcambia entre evaluación inmediata y evaluación diferida según la pureza de la función argumento- Aunque una biblioteca use internamente evaluación diferida o evaluación paralela de forma selectiva, el significado desde la perspectiva del cliente puede no cambiar
Paralelismo, concurrencia y abstracción
- Flix facilita evaluar código puro en paralelo, y permite escribir una implementación paralela de
List.mapcon la construcciónpar - La construcción
parusa internamente VirtualThread ligeros - Soporta concurrencia estructurada: los threads creados dentro de una región específica no pueden sobrevivir fuera del ciclo de vida de esa región
- En el ejemplo, se crean dos threads dentro de una nueva región llamada
rc - El flujo de control no sale de la región hasta que ambos threads hayan terminado
- En el ejemplo, se crean dos threads dentro de una nueva región llamada
- Para abstracciones de tipos que soportan operaciones comunes, se usan traits
- El trait
Eqexpresa el concepto de igualdad y se usa en toda la biblioteca estándar
- El trait
- Los tipos de kind de orden superior permiten abstraer constructores de tipos
- Tanto
OptioncomoListimplementanFoldable - La biblioteca estándar incluye traits comunes como
Monoid,FunctoryFoldable
- Tanto
Tipos y efectos asociados, y for-yield
- Flix soporta tipos asociados, que permiten que el tipo de una firma de instancia dependa del tipo de la instancia
- El ejemplo del trait
Collpermite que cada instancia de colección defina el tipo de sus elementos mediante el tipo asociadoElm
- El ejemplo del trait
- Los efectos asociados hacen que el efecto de un miembro de trait dependa del tipo de la instancia
- Facilitan abstraer en conjunto operaciones puras y operaciones con efectos, así como estructuras de datos mutables e inmutables
- Si se agrega el efecto asociado
Aefal traitColl, pueden añadirse instancias de colecciones mutables
forM-yield es una estructura monádica similar a lasfor-comprehensions de Scala y a la notacióndode Haskell- Es azúcar sintáctica para usar
pointyflatMap, provistos por el traitMonad
- Es azúcar sintáctica para usar
forAes una expresión aplicativa basada en el traitApplicative- Es una estructura que ayuda a escribir fácilmente código de manejo de errores usando el tipo de datos
Validation[e, t]
- Es una estructura que ayuda a escribir fácilmente código de manejo de errores usando el tipo de datos
Interoperabilidad con Java y Datalog
- Flix soporta interoperabilidad con Java, lo que permite reutilizar la Java Standard Library y código del ecosistema Java
- Incluye acceso al ecosistema mediante Maven
- Soporta creación de objetos, llamadas a métodos, excepciones y extensión de clases e interfaces
- El soporte integrado de Datalog es una de las funciones distintivas de Flix
- Datalog permite expresar de forma concisa varios problemas de punto fijo, incluidos los de alcanzabilidad en grafos
- Las restricciones de Datalog son valores de primera clase
- Pueden pasarse a funciones o devolverse desde funciones
- Pueden almacenarse en estructuras de datos
- Pueden componerse con otras restricciones de Datalog y resolverse
- Esto permite expresar familias de programas Datalog
- Flix también soporta restricciones de Datalog enriquecidas con semántica de retículos
- Hay un ejemplo que calcula fechas de entrega de piezas y subcomponentes
- Un automóvil depende del chasis y del motor, y puede ensamblarse después de esperar el ensamblaje de cada componente
- Los subcomponentes también pueden depender de otros subcomponentes, por lo que el problema es recursivo
- Las restricciones de Datalog con semántica de retículos son una de las funciones avanzadas de Flix y requieren conocimientos de teoría de retículos y puntos fijos
Biblioteca estándar y lista de funciones
- Flix incluye una biblioteca estándar que ofrece más de 3,100 funciones
- El módulo
Listofrece más de 100 funciones - El trait
Foldableofrece más de 47 funciones - La biblioteca completa puede explorarse en api.flix.dev
- El módulo
- La lista de funcionalidades incluye lo siguiente
- Tipos de datos algebraicos, pattern matching y funciones de primera clase
- Registros extensibles y polimorfismo paramétrico
- Traits, tipos de kind de orden superior, tipos y efectos asociados
- Polimorfismo de efectos y subefectos, reflexión de pureza
- Concurrencia estilo CSP, canales con buffer y sin buffer
- Restricciones de Datalog de primera clase, interoperabilidad con Java
- Tipos primitivos sin boxeo, sintaxis basada en palabras clave
forM,forAy holes de expresión- Compilación a bytecode de JVM, eliminación completa de llamadas de cola
- Arquitectura de compilador resiliente y paralela, errores legibles para humanos
Arquitectura y rendimiento del compilador
- El compilador de Flix tiene una arquitectura resiliente, incremental y paralela
- Todas las etapas del compilador son paralelas, y en una máquina de 24 núcleos puede aprovechar las mejoras de velocidad de cada etapa
- En máquinas multinúcleo, es posible obtener mejoras de velocidad de 5x–7x
- Al recompilar código ya compilado en la misma instancia del compilador, la compilación incremental puede ofrecer mejoras de velocidad significativas
- Las cifras de rendimiento con una CPU Apple M2 Pro de 10 núcleos y OpenJDK 21 son las siguientes
- Rendimiento del compilador completo: 60,159 líneas/segundo
- Rendimiento solo del frontend: 140,382 líneas/segundo
- Los comandos de reproducción son
java -jar flix.jar Xperf --n 21yjava -jar flix.jar Xperf --frontend --n 21
- Este rendimiento se logra mientras se soportan funciones del lenguaje costosas, como inferencia de tipos y efectos, monomorfización y optimización de programa completo
- El rendimiento del compilador está determinado principalmente por el rendimiento de la CPU y el ancho de banda de memoria
Soporte para Visual Studio Code e integración de herramientas
- El compilador de Flix se integra con Visual Studio Code para ofrecer un entorno de desarrollo
- La extensión de VSCode usa el compilador real de Flix, por lo que hay una correspondencia 1:1 entre la extensión y el compilador
- Si VSCode no reporta errores, no hay errores
- Cuando no hay errores, VSCode no reporta errores falsos
- La extensión de VSCode soporta las siguientes funciones
- Resaltado de sintaxis basado en semántica
- Diagnósticos de errores del compilador en línea
- Autocompletado mientras se escribe, autocompletado sensible al contexto, autocompletado de instancias de traits y completado de holes basado en tipos
- Snippets e inlay hints
- Hover que muestra el tipo y el efecto de las expresiones
- Ir a definiciones de funciones, variables locales y enum
- Buscar referencias de funciones, variables locales y enum, y buscar implementaciones de traits
- Lista de símbolos de documento y de workspace
- Renombrado de variables locales y funciones
- Ejecución de
mainy ejecución de tests desde el editor
- Flix integra muchas herramientas directamente en el compilador
- OCaml usa
ocaml-lspcomo LSP,utopcomo REPL,dunecomo herramienta de build yopamcomo gestor de paquetes - Haskell usa
HLScomo LSP,ghcicomo REPL,cabalystackcomo herramientas de build y gestores de paquetes, yHackagecomo repositorio de paquetes - Flix ofrece compilador, LSP, REPL, herramienta de build y gestor de paquetes mediante
flix, y su repositorio de paquetes es GitHub
- OCaml usa
Estado de desarrollo, objetivo JVM y escala del proyecto
- Flix es desarrollado y mantenido por investigadores de lenguajes de programación de Aarhus University, Dinamarca
- Las instituciones colaboradoras son University of Waterloo en Canadá, University of Tubingen en Alemania y Copenhagen University en Dinamarca
- La participación de una comunidad global de contribuidores de código abierto está creciendo, y se invita a contribuir
- Las estadísticas del proyecto son las siguientes
- Pull Requests fusionados: más de 4,900
- Issues resueltos: más de 3,100
- Contribuidores: más de 70
- Base de código del compilador: más de 272,000 líneas
- Flix apunta a la JVM
- La JVM cuenta con implementaciones open source y comerciales probadas, como OpenJDK, J9, Azul y Graal
- Puede usarse en Mac, Linux y Windows
- Las JVM modernas ofrecen varios garbage collectors recientes
- Tiene buen soporte para concurrencia y paralelismo, incluidos los threads ligeros de Java 21
- Cuenta con soporte de herramientas, incluidos debuggers y profilers
- La integración con Maven permite acceder al rico ecosistema de paquetes de la plataforma Java
- La financiación total es de 1.1 millones de euros, lo que ayuda a garantizar la continuidad e independencia del proyecto
Aún no hay comentarios.