Fix RHole, add test files, papers, piforall examples

This commit is contained in:
2024-08-22 22:07:45 -07:00
parent 9db5649446
commit 2c20cadd09
9 changed files with 238 additions and 3 deletions

54
piforall/Fix.pi Normal file
View File

@@ -0,0 +1,54 @@
-- Can we define the Y combinator in pi-forall?
-- Yes! See below.
-- Note: pi-forall allows recursive definitions,
-- so this is not necessary at all.
module Fix where
-- To type check the Y combinator, we need to have a type
-- D such that D ~~ D -> D
data D (A : Type) : Type where
F of (_ : D A -> D A)
V of (_ : A)
unV : [A:Type] -> D A -> A
unV = \[A] v.
case v of
V y -> y
F f -> TRUSTME
unF :[A:Type] -> D A -> D A -> D A
unF = \[A] v x .
case v of
F f -> f x
V y -> TRUSTME
-- Here's the Y-combinator. To make it type
-- check, we need to add the appropriate conversions
-- into and out of the D type.
fix : [A:Type] -> (A -> A) -> A
fix = \ [A] g.
let omega =
( \x. V (g (unV [A] (unF [A] x x)))
: D A -> D A) in
unV [A] (omega (F omega))
-- Example use case
data Nat : Type where
Zero
Succ of ( _ : Nat)
fix_add : Nat -> Nat -> Nat
fix_add = fix [Nat -> Nat -> Nat]
\radd. \x. \y.
case x of
Zero -> y
Succ n -> Succ (radd n y)
test : fix_add 5 2 = 7
test = Refl

74
piforall/Lennart.pi Normal file
View File

@@ -0,0 +1,74 @@
module Lennart where
-- stack exec -- pi-forall Lennart.pi
-- with unbind / subst
-- 7.81s user 0.52s system 97% cpu 8.568 total
-- with substBind
-- 3.81s user 0.28s system 94% cpu 4.321 total
import Fix
bool : Type
bool = [C : Type] -> C -> C -> C
false : bool
false = \[C]. \f.\t.f
true : bool
true = \[C]. \f.\t.t
nat : Type
nat = [C : Type] -> C -> (nat -> C) -> C
zero : nat
zero = \[C].\z.\s.z
succ : nat -> nat
succ = \n.\[C].\z.\s. s n
one : nat
one = succ zero
two : nat
two = succ one
three : nat
three = succ two
isZero : nat -> bool
isZero = \n.n [bool] true (\m.false)
const : [A:Type] -> A -> A -> A
const = \[A].\x.\y.x
prod : Type -> Type -> Type
prod = \A B. [C:Type] -> (A -> B -> C) -> C
pair : [A :Type] -> [B: Type] -> A -> B -> prod A B
pair = \[A][B] a b. \[C] p. p a b
fst : [A:Type] -> [B:Type] -> prod A B -> A
fst = \[A][B] ab. ab [A] (\a.\b.a)
snd : [A:Type] -> [B:Type] -> prod A B -> B
snd = \[A][B] ab.ab [B] (\a.\b.b)
add : nat -> nat -> nat
add = fix [nat -> nat -> nat]
\radd . \x.\y. x [nat] y (\ n. succ (radd n y))
mul : nat -> nat -> nat
mul = fix [nat -> nat -> nat]
\rmul. \x.\y. x [nat] zero (\ n. add y (rmul n y))
fac : nat -> nat
fac = fix [nat -> nat]
\rfac. \x. x [nat] one (\ n. mul x (rfac n))
eqnat : nat -> nat -> bool
eqnat = fix [nat -> nat -> bool]
\reqnat. \x. \y.
x [bool]
(y [bool] true (\b.false))
(\x1.y [bool] false (\y1. reqnat x1 y1))
sumto : nat -> nat
sumto = fix [nat -> nat]
\rsumto. \x. x [nat] zero (\n. add x (rsumto n))
n5 : nat
n5 = add two three
n6 : nat
n6 = add three three
n17 : nat
n17 = add n6 (add n6 n5)
n37 : nat
n37 = succ (mul n6 n6)
n703 : nat
n703 = sumto n37
n720 : nat
n720 = fac n6
t : (eqnat n720 (add n703 n17)) = true
t = Refl