Agda-2.3.2.2: benchmark/cwf/CwF.agda
module CwF where
open import Setoid
open EqChain
infixr 30 _⇒_
infixl 50 _/_ _/ˢ_
infixr 45 _◄_
infixl 45 _▷_
Cxt : Set
Cxt = Setoid
_⇒_ : Cxt -> Cxt -> Set
Γ ⇒ Δ = El (Γ ==> Δ)
Type : Cxt -> Set
Type Γ = Fam Γ
_/_ : {Γ Δ : Cxt} -> Type Γ -> (Δ ⇒ Γ) -> Type Δ
A / σ = A ○ σ
lem-/id : {Γ : Cxt}{A : Type Γ} -> A / id == A
lem-/id = lem-○-id
Term : (Γ : Cxt) -> Type Γ -> Set
Term Γ A = El (Π Γ A)
_◄_ : {Γ : Cxt}{A B : Type Γ} -> B == A -> Term Γ A -> Term Γ B
B=A ◄ u = eqΠ refl B=A << u
_/ˢ_ : {Γ Δ : Cxt}{A : Type Γ} -> Term Γ A -> (σ : Δ ⇒ Γ) -> Term Δ (A / σ)
u /ˢ σ = u ∘ σ
_▷_ : (Γ : Cxt) -> Type Γ -> Cxt
Γ ▷ A = Σ Γ A
wk : {Γ : Cxt}(A : Type Γ) -> Γ ▷ A ⇒ Γ
wk A = ƛ fst \ x y x=y -> fst-eq x=y
vz : {Γ : Cxt}(A : Type Γ) -> Term (Γ ▷ A) (A / wk A)
vz A = ƛ snd \ x y x=y -> snd-eq x=y
ext : {Γ Δ : Cxt}(A : Type Γ)(σ : Δ ⇒ Γ)(u : Term Δ (A / σ)) -> Δ ⇒ Γ ▷ A
ext A σ u = ƛ (\x -> (σ # x , u # x))
\x y x=y -> eqInΣ refl (#-cong-R σ x=y) (#-cong-R u x=y)
lem-/-· : {Γ Δ Θ : Cxt}(A : Type Γ)(σ : Δ ⇒ Γ)(δ : Θ ⇒ Δ) ->
A / σ · δ == A / σ / δ
lem-/-· A σ δ = eqFam refl \x y x=y ->
!-cong-R A (sym (cast-id' _ (#-cong-R σ (#-cong-R δ (cast-id' _ (sym x=y))))))
lem-wk-∘-ext : {Γ Δ : Cxt}(A : Type Δ)(σ : Γ ⇒ Δ)(u : Term Γ (A / σ)) ->
wk A ∘ ext A σ u == σ
lem-wk-∘-ext A (ƛ σ pσ) u = eqInΠ refl pσ
lem-vz-/-ext : {Γ Δ : Cxt}(A : Type Δ)(σ : Γ ⇒ Δ)(u : Term Γ (A / σ)) ->
vz A /ˢ (ext A σ u) == u
lem-vz-/-ext A σ (ƛ u pu) = eqInΠ refl pu
-- (σ , u) ∘ δ == (σ ∘ δ , u / δ)
lem-ext-∘ : {Γ Δ Θ : Cxt}{A : Type Γ}(σ : Δ ⇒ Γ)(δ : Θ ⇒ Δ)(u : Term Δ (A / σ)) ->
ext A σ u · δ == ext A (σ · δ) (lem-/-· A σ δ ◄ u /ˢ δ)
lem-ext-∘ σ δ u = eqInΠ refl \x y x=y ->
eqInΣ refl
(cast-irr _ _ (#-cong-R σ (#-cong-R δ (cast-irr _ _ x=y))))
(cast-irr _ _ (#-cong-R u (#-cong-R δ (cast-irr _ _ x=y))))
<_> : {Γ : Cxt}{A : Type Γ} -> Term Γ A -> Γ ⇒ Γ ▷ A
< u > = ext _ id (lem-○-id ◄ u)
lift : {Γ Δ : Cxt}(A : Type Γ)(σ : Δ ⇒ Γ) -> Δ ▷ (A / σ) ⇒ Γ ▷ A
lift A σ = ƛ (\x -> σ # fst x , snd x)
\x y x=y -> eqInΣ refl (#-cong-R σ (fst-eq x=y)) (snd-eq x=y)
curryFam : {A : Setoid}{F : Fam A} -> Fam (Σ A F) -> (x : El A) -> Fam (F ! x)
curryFam G x = fam (\y -> G ! (x , y))
\z w z=w -> !-cong-R G (eqInΣ refl refl z=w)
Pi : {Γ : Cxt}(A : Type Γ)(B : Type (Γ ▷ A)) -> Type Γ
Pi A B = fam (\x -> Π (A ! x) (curryFam B x))
\x y x=y ->
eqΠ (!-cong-R A (sym x=y))
(eqFam (!-cong-R A (sym x=y)) \z w z=w ->
!-cong-R B (eqInΣ refl x=y z=w)
)
lem-Pi-/ : {Γ Δ : Cxt}(A : Type Γ)(B : Type (Γ ▷ A))(σ : Δ ⇒ Γ) ->
Pi A B / σ == Pi (A / σ) (B / lift A σ)
lem-Pi-/ A B σ = eqFam refl \x y x=y ->
eqΠ (Aσ-eq x=y)
(eqFam (Aσ-eq x=y) \z w z=w ->
!-cong-R B (eqInΣ refl (#-cong-R σ x=y) z=w)
)
where
Aσ-eq : forall {x y} -> x == y -> A ! σ # y == A ! σ # x
Aσ-eq x=y = !-cong-R A (#-cong-R σ (sym x=y))
lam : {Γ : Cxt}{A : Type Γ}{B : Type (Γ ▷ A)} -> Term (Γ ▷ A) B -> Term Γ (Pi A B)
lam {A = A} f =
ƛ (\γ -> ƛ (\x -> f # (γ , x)) (prf₁ γ)) prf₂
where
prf₁ : forall γ x y x=y -> _
prf₁ = \γ x y x=y -> #-cong-R f (eqInΣ refl refl x=y)
prf₂ = \x y x=y ->
eqInΠ (!-cong-R A (sym x=y)) \z w z=w ->
#-cong-R f (eqInΣ refl x=y z=w)
app : {Γ : Cxt}(A : Type Γ)(B : Type (Γ ▷ A))
(v : Term Γ (Pi A B))(u : Term Γ A) -> Term Γ (B / < u >)
app A B v u = ƛ (\γ -> prf₁ γ << v # γ # (u # γ)) prf₂
where
lem : forall γ -> < u > # γ == (γ , u # γ)
lem γ = eqInΣ refl refl (#-cong (lem-○-id ◄ u) u (sym (cast-id _)) refl)
prf₁ : forall γ -> (B / < u >) ! γ == B ! (γ , u # γ)
prf₁ γ = !-cong-R B (lem γ)
prf₂ = \x y x=y -> cast-irr _ _ (#-cong (v # x) (v # y)
(#-cong-R v x=y)
(#-cong-R u x=y)
)
lem-β : {Γ : Cxt}(A : Type Γ)(B : Type (Γ ▷ A))
(v : Term (Γ ▷ A) B)(u : Term Γ A) ->
app A B (lam v) u == v /ˢ < u >
lem-β A B v u = eqInΠ refl \x y x=y ->
sym (cast-id' _
(#-cong-R v
(eqInΣ refl (sym x=y)
(#-cong (lem-○-id ◄ u) u (sym (cast-id _)) (sym x=y)))
)
)
-- The stack blows when trying to prove η.
-- I'm not sure it does anymore, but I have no idea how to prove η,
-- I struggled just giving the type.
-- lem-η : {Γ : Cxt}(A : Type Γ)(B : Type (Γ ▷ A))
-- (v : Term Γ (Pi A B)) →
-- v == lam (app (A / wk A) (B / lift A (wk A)) (sym (lem-Pi-/ A B (wk A)) ◄ v /ˢ wk A) (vz A))
-- lem-η {Γ} A B (ƛ f pf) =
-- eqInΠ =S=-refl λ γ δ γ=δ →
-- proof f γ ≡ ƛ (_#_ (f γ)) (λ _ _ → #-cong-R (f γ)) by η (f γ)
-- ≡ _ by eqInΠ (!-cong-R A (sym γ=δ)) (λ x y x=y →
-- proof f γ # x
-- ≡ (_ << (_ << f (_ << δ))) # y by {!!}
-- qed)
-- qed