Epigram es un lenguaje de programación funcional con tipos dependientes y un entorno de desarrollo integrado (IDE) que normalmente se incluye con el lenguaje. El sistema de tipos de Epigram es lo suficientemente fuerte como para expresar especificaciones de programas . El objetivo es respaldar una transición fluida desde la programación ordinaria a programas integrados y pruebas cuya corrección pueda ser verificada y certificada por el compilador . Epigram explota la correspondencia de Curry-Howard , también denominada principio de proposiciones como tipos , y se basa en la teoría de tipos intuicionista .
El prototipo de Epigram fue implementado por Conor McBride en base al trabajo conjunto con James McKinna. Su desarrollo es continuado por el grupo Epigram en Nottingham , Durham , St Andrews y Royal Holloway, Universidad de Londres en el Reino Unido (UK). La implementación experimental actual del sistema Epigram está disponible de forma gratuita junto con un manual de usuario, un tutorial y algo de material de referencia. El sistema se ha utilizado en Linux , Windows y macOS .
Actualmente no se mantiene y la versión 2, que pretendía implementar la teoría de tipos observacional, nunca se lanzó oficialmente, pero existe en GitHub .
Epigram utiliza una sintaxis de deducción natural bidimensional , con versiones en LaTeX y ASCII . A continuación, se muestran algunos ejemplos de The Epigram Tutorial :
La siguiente declaración define los números naturales :
( ! ( ! ( n : Nat ! datos !---------! donde !----------! ; !-----------! ! Nat : * ) ! cero : Nat ) ! suc n : Nat )
La declaración dice que Nat
es un tipo con clase *
(es decir, es un tipo simple) y dos constructores: zero
y suc
. El constructor suc
toma un único Nat
argumento y devuelve un Nat
. Esto es equivalente a la declaración de Haskelldata Nat = Zero | Suc Nat
" ".
En LaTeX, el código se muestra como:
La notación de línea horizontal se puede leer como "suponiendo que (lo que está en la parte superior) es verdadero, podemos inferir que (lo que está en la parte inferior) es verdadero". Por ejemplo, "suponiendo n
que es del tipo Nat
, entonces suc n
es del tipo Nat
". Si no hay nada en la parte superior, entonces la declaración inferior siempre es verdadera: " zero
es del tipo Nat
(en todos los casos)".
...Y en ASCII:
IndNat : todos P : Nat -> * => P cero -> ( todos n : Nat => P n -> P ( suc n )) -> todos n : Nat => P n NatInd P mz ms cero => mz NatInd P mz ms ( suc n ) => ms n ( NatInd P mz ms n )
...Y en ASCII:
más x y <= rec x { más x y <= caso x { más cero y => y más ( suc x ) y => suc ( más x y ) } }
Epigram es esencialmente un cálculo lambda tipado con extensiones de tipos de datos algebraicos generalizados , excepto por dos extensiones. Primero, los tipos son entidades de primera clase, de tipo ; los tipos son expresiones arbitrarias de tipo , y la equivalencia de tipos se define en términos de las formas normales de los tipos. Segundo, tiene un tipo de función dependiente; en lugar de , , donde está ligado al valor que el argumento de la función (de tipo ) eventualmente toma.
Los tipos totalmente dependientes, tal como se implementan en Epigram, son una abstracción poderosa. (A diferencia de Dependent ML , los valores de los que dependen pueden ser de cualquier tipo válido). Se puede encontrar una muestra de las nuevas capacidades de especificación formal que brindan los tipos dependientes en el Tutorial de Epigram .