{- An implementation of the (typed) SKI-calculus. References: [0] Lectures on the Curry-Howard-Isomorphism -- SΓΈrensen, Urzyczyin [1] To Mock a Mockingbird -- Smullyan -} open import Data.Nat open import Data.Nat.Properties open import Data.Product open import Relation.Nullary.Decidable using (yes ; no) open import Relation.Binary.Definitions using (DecidableEquality) open import Relation.Binary.PropositionalEquality hiding ([_]) open import Relation.Nullary using (Β¬_) {- The implementation is parametric over a set π“₯ of variables (on which propositional equality is decidable) -} module ski (π“₯ : Set) (_β‰ˆ_ : DecidableEquality π“₯) where -- Syntax of terms as an inductive type infixl 5 _βˆ™_ data CL : Set where `_ : π“₯ β†’ CL K : CL S : CL _βˆ™_ : CL β†’ CL β†’ CL -- one-step reduction relation infix 4 _⟢_ data _⟢_ : CL β†’ CL β†’ Set where k : βˆ€ {F G : CL} β†’ K βˆ™ F βˆ™ G ⟢ F s : βˆ€ {F G H : CL} β†’ S βˆ™ F βˆ™ G βˆ™ H ⟢ F βˆ™ H βˆ™ (G βˆ™ H) appβ‚— : βˆ€ {F F' G : CL} β†’ F ⟢ F' β†’ ---------------- F βˆ™ G ⟢ F' βˆ™ G appα΅£ : βˆ€ {F G G' : CL} β†’ G ⟢ G' β†’ ------------- F βˆ™ G ⟢ F βˆ™ G' module mstep where infix 4 _β† _ -- reflexive transitive closure of _⟢_ infix 3 _∎ infixr 2 _⟢⟨_⟩_ data _β† _ : CL β†’ CL β†’ Set where _∎ : βˆ€ (F : CL) β†’ F β†  F cons : βˆ€ {F G H : CL} β†’ F ⟢ G β†’ G β†  H β†’ F β†  H {- The following definitions are some syntax sugar for proofs on the step relation -} -- one step pattern _⟢⟨_⟩_ F F⟢G Gβ† H = cons {F} F⟢G Gβ† H infix 1 begin_ begin_ : βˆ€ {F G : CL} β†’ F β†  G β†’ F β†  G begin step = step -- injection of a singular step into the multi-step relation once : βˆ€ {F G : CL} β†’ F ⟢ G β†’ F β†  G once {G = G} step = cons step (G ∎) -- multi step infixr 2 _β† βŸ¨_⟩_ _β† βŸ¨_⟩_ : βˆ€ (F : CL) {G H : CL} β†’ F β†  G β†’ G β†  H β†’ F β†  H _β† βŸ¨_⟩_ F (_ ∎) step' = step' _β† βŸ¨_⟩_ F (cons {G = G} x step) step' = cons x (_β† βŸ¨_⟩_ G step step') -- left and right congruence of the multi-step relation mappβ‚— : βˆ€ {F G H : CL} β†’ F β†  H β†’ (F βˆ™ G) β†  (H βˆ™ G) mappβ‚— {F} {G} (_ ∎) = F βˆ™ G ∎ mappβ‚— (cons F⟢H' Gβ† H) = cons (appβ‚— F⟢H') (mappβ‚— Gβ† H) mappα΅£ : βˆ€ {F G H : CL} β†’ G β†  H β†’ (F βˆ™ G) β†  (F βˆ™ H) mappα΅£ {F} {_} {H} (_ ∎) = F βˆ™ H ∎ mappα΅£ (cons G⟢H' H'β† H) = cons (appα΅£ G⟢H') (mappα΅£ H'β† H) open mstep {- Let's define some of the combinator birds from [1]: -} module birds where -- Identity (Idiot) bird I : CL I = S βˆ™ K βˆ™ K I-step : βˆ€ {F : CL} β†’ I βˆ™ F β†  F I-step {F} = begin I βˆ™ F ⟢⟨ s ⟩ K βˆ™ F βˆ™ (K βˆ™ F) ⟢⟨ k ⟩ F ∎ -- Bluebird B : CL B = S βˆ™ (K βˆ™ S) βˆ™ K B-step : βˆ€ {F G X : CL} β†’ B βˆ™ F βˆ™ G βˆ™ X β†  F βˆ™ (G βˆ™ X) B-step {F} {G} {X} = begin B βˆ™ F βˆ™ G βˆ™ X ⟢⟨ appβ‚— (appβ‚— s) ⟩ K βˆ™ S βˆ™ F βˆ™ (K βˆ™ F) βˆ™ G βˆ™ X ⟢⟨ appβ‚— (appβ‚— (appβ‚— k)) ⟩ S βˆ™ (K βˆ™ F) βˆ™ G βˆ™ X ⟢⟨ s ⟩ K βˆ™ F βˆ™ X βˆ™ (G βˆ™ X) ⟢⟨ appβ‚— k ⟩ F βˆ™ (G βˆ™ X) ∎ -- Warbler W : CL W = S βˆ™ S βˆ™ (K βˆ™ I) W-step : βˆ€ {F G : CL} β†’ W βˆ™ F βˆ™ G β†  F βˆ™ G βˆ™ G W-step {F} {G} = begin W βˆ™ F βˆ™ G ⟢⟨ appβ‚— s ⟩ S βˆ™ F βˆ™ (K βˆ™ I βˆ™ F) βˆ™ G ⟢⟨ s ⟩ F βˆ™ G βˆ™ (K βˆ™ I βˆ™ F βˆ™ G) ⟢⟨ appα΅£ (appβ‚— k) ⟩ F βˆ™ G βˆ™ (I βˆ™ G) β† βŸ¨ mappα΅£ I-step ⟩ F βˆ™ G βˆ™ G ∎ -- Cardinal C : CL C = S βˆ™ (B βˆ™ B βˆ™ S) βˆ™ (K βˆ™ K) C-step : βˆ€ {F G H : CL} β†’ C βˆ™ F βˆ™ G βˆ™ H β†  F βˆ™ H βˆ™ G C-step {F} {G} {H} = begin C βˆ™ F βˆ™ G βˆ™ H ⟢⟨ appβ‚— (appβ‚— s) ⟩ B βˆ™ B βˆ™ S βˆ™ F βˆ™ (K βˆ™ K βˆ™ F) βˆ™ G βˆ™ H β† βŸ¨ mappβ‚— (mappβ‚— (mappβ‚— B-step)) ⟩ B βˆ™ (S βˆ™ F) βˆ™ (K βˆ™ K βˆ™ F) βˆ™ G βˆ™ H β† βŸ¨ mappβ‚— B-step ⟩ S βˆ™ F βˆ™ (K βˆ™ K βˆ™ F βˆ™ G) βˆ™ H ⟢⟨ s ⟩ F βˆ™ H βˆ™ (K βˆ™ K βˆ™ F βˆ™ G βˆ™ H) ⟢⟨ appα΅£ (appβ‚— (appβ‚— k)) ⟩ F βˆ™ H βˆ™ (K βˆ™ G βˆ™ H) ⟢⟨ appα΅£ k ⟩ F βˆ™ H βˆ™ G ∎ -- Mockingbird M : CL M = S βˆ™ I βˆ™ I M-step : βˆ€ {F : CL} β†’ M βˆ™ F β†  F βˆ™ F M-step {F} = begin M βˆ™ F ⟢⟨ s ⟩ I βˆ™ F βˆ™ (I βˆ™ F) β† βŸ¨ mappβ‚— I-step ⟩ F βˆ™ (I βˆ™ F) β† βŸ¨ mappα΅£ I-step ⟩ F βˆ™ F ∎ -- Applying the mockingbird to itself yields a term that reduces to itself loop : M βˆ™ M β†  M βˆ™ M loop = M-step open birds {- Relating the SKI-calculus to the Ξ»-calculus. Taken from chapter 5.4 in [0] -} module combinatory-abstraction where -- Substituting a variable for a term _[_/_] : CL β†’ CL β†’ π“₯ β†’ CL (` y) [ B / x ] with x β‰ˆ y ... | yes p = B ... | no Β¬p = ` y K [ B / x ] = K S [ B / x ] = S (A βˆ™ C) [ B / x ] = (A [ B / x ]) βˆ™ (C [ B / x ]) -- combinary abstraction ƛ⋆_↦_ : π“₯ β†’ CL β†’ CL ƛ⋆ v ↦ (` x) with v β‰ˆ x ... | yes _ = I ... | no _ = K βˆ™ (` x) ƛ⋆ v ↦ K = K βˆ™ K ƛ⋆ v ↦ S = K βˆ™ S ƛ⋆ v ↦ (B βˆ™ C) = S βˆ™ (ƛ⋆ v ↦ B) βˆ™ (ƛ⋆ v ↦ C) -- combinary abstraction is beta reductive beta : βˆ€ {x : π“₯} {B : CL} β†’ (A : CL) β†’ (ƛ⋆ x ↦ A) βˆ™ B β†  A [ B / x ] beta {x} (` y) with x β‰ˆ y ... | yes p = I-step ... | no Β¬p = once k beta K = once k beta S = once k beta {x} {G} (B βˆ™ C) = begin (ƛ⋆ x ↦ (B βˆ™ C)) βˆ™ G ⟢⟨ s ⟩ (ƛ⋆ x ↦ B) βˆ™ G βˆ™ ((ƛ⋆ x ↦ C) βˆ™ G) β† βŸ¨ mappβ‚— (beta B) ⟩ (B [ G / x ]) βˆ™ ((ƛ⋆ x ↦ C) βˆ™ G) β† βŸ¨ mappα΅£ (beta C) ⟩ ((B βˆ™ C) [ G / x ]) ∎ infix 5 _∈_ data _∈_ : π“₯ β†’ CL β†’ Set where in-here : βˆ€ {x : π“₯} β†’ x ∈ ` x in-left : βˆ€ {x : π“₯} {F G : CL} β†’ x ∈ F β†’ x ∈ (F βˆ™ G) in-right : βˆ€ {x : π“₯} {F G : CL} β†’ x ∈ G β†’ x ∈ (F βˆ™ G) open import Data.Empty no-intro : βˆ€ {x : π“₯} (F : CL) β†’ Β¬ (x ∈ F) β†’ βˆ€ (v : π“₯) β†’ Β¬ (x ∈ (ƛ⋆ v ↦ F)) no-intro {x} (` y) xβˆ‰F v xβˆˆΞ»β‹†F with v β‰ˆ y ... | yes p with xβˆˆΞ»β‹†F no-intro {x} (` y) xβˆ‰F v xβˆˆΞ»β‹†F | yes p | in-left (in-left ()) no-intro {x} (` y) xβˆ‰F v xβˆˆΞ»β‹†F | yes p | in-left (in-right ()) no-intro {x} (` y) xβˆ‰F v xβˆˆΞ»β‹†F | no Β¬p with xβˆˆΞ»β‹†F no-intro {x} (` y) xβˆ‰F v xβˆˆΞ»β‹†F | no Β¬p | in-right p = βŠ₯-elim (xβˆ‰F p) no-intro K xβˆ‰F v (in-left xβˆˆΞ»β‹†F) = xβˆ‰F xβˆˆΞ»β‹†F no-intro K xβˆ‰F v (in-right xβˆˆΞ»β‹†F) = xβˆ‰F xβˆˆΞ»β‹†F no-intro S xβˆ‰F v (in-left ()) no-intro S xβˆ‰F v (in-right xβˆˆΞ»β‹†F) = xβˆ‰F xβˆˆΞ»β‹†F no-intro (F βˆ™ G) xβˆ‰F v (in-left (in-right xβˆˆΞ»β‹†F)) = no-intro F (Ξ» z β†’ xβˆ‰F (in-left z)) v xβˆˆΞ»β‹†F no-intro (F βˆ™ G) xβˆ‰F v (in-right xβˆˆΞ»β‹†F) = no-intro G (Ξ» z β†’ xβˆ‰F (in-right z)) v xβˆˆΞ»β‹†F module cl-lambda (x y z : π“₯) (xβ‰’y : x β‰’ y) (xβ‰’z : x β‰’ z) (yβ‰’z : y β‰’ z) where open import lambda π“₯ _β‰ˆ_ renaming (mappβ‚— to lmappβ‚— ; mappα΅£ to lmappα΅£) ⟨_βŸ©Ξ› : CL β†’ Ξ› ⟨ ` v βŸ©Ξ› = ` v ⟨ K βŸ©Ξ› = Ζ› x ↦ Ζ› y ↦ ` x ⟨ S βŸ©Ξ› = Ζ› x ↦ Ζ› y ↦ Ζ› z ↦ (` x βˆ™ ` z) βˆ™ (` y βˆ™ ` z) ⟨ F βˆ™ G βŸ©Ξ› = ⟨ F βŸ©Ξ› βˆ™ ⟨ G βŸ©Ξ› ⟨_⟩CL : Ξ› β†’ CL ⟨ ` v ⟩CL = ` v ⟨ m βˆ™ n ⟩CL = ⟨ m ⟩CL βˆ™ ⟨ n ⟩CL ⟨ Ζ› v ↦ m ⟩CL = ƛ⋆ v ↦ ⟨ m ⟩CL lemma : βˆ€ (t : Ξ›) β†’ ⟨ ⟨ t ⟩CL βŸ©Ξ› β† Ξ² t lemma (` x) = ` x ∎ lemma (t βˆ™ h) = Ξ²egin _ β† Ξ²βŸ¨ lmappβ‚— (lemma t) ⟩ _ β† Ξ²βŸ¨ lmappα΅£ (lemma h) ⟩ _ ∎ lemma (Ζ› x ↦ t) = {!!} foo : ⟨ Ζ› y ↦ ` y βˆ™ ` y ⟩CL ≑ S βˆ™ I βˆ™ I foo with y β‰ˆ y ... | yes _ = refl ... | no Β¬p = βŠ₯-elim (Β¬p refl) _ : ⟨ S βˆ™ I βˆ™ I βŸ©Ξ› β‰’ (Ζ› y ↦ ` y βˆ™ ` y) _ = Ξ» () _ : ⟨ ⟨ S βˆ™ K βˆ™ K βŸ©Ξ› ⟩CL β‰’ S βˆ™ K βˆ™ K _ = Ξ» () -- lemma : βˆ€ {F G : CL} β†’ -- F ⟢ G β†’ -- ⟨ F βŸ©Ξ› β† Ξ² ⟨ G βŸ©Ξ› -- lemma {F} {G} (k {G = H}) = Ξ²egin -- ⟨ K βˆ™ G βˆ™ H βŸ©Ξ› β† Ξ²βŸ¨ lmappβ‚— (Ξ²-once (Ξ² {!!})) ⟩ -- {!!} β† Ξ²βŸ¨ {!!} ⟩ -- ⟨ G βŸ©Ξ› ∎ -- lemma s = {!!} -- lemma (appβ‚— x) = {!!} -- lemma (appα΅£ x) = {!!} module typing where open import Data.List open import Data.List.Membership.Propositional using (_∈_) open import Data.List.Relation.Unary.Any using (here ; there) infixr 5 _β‡’_ data type : Set where ⋆ : type _β‡’_ : type β†’ type β†’ type context : Set context = List (π“₯ Γ— type) _βˆˆβ‚_ : π“₯ β†’ context β†’ Set v βˆˆβ‚ Ξ“ = v ∈ (Data.List.map proj₁ Ξ“) _!!_ : {v : π“₯} β†’ (Ξ“ : context) β†’ (v βˆˆβ‚ Ξ“) β†’ type [] !! () (x ∷ Ξ“) !! here px = projβ‚‚ x (x ∷ Ξ“) !! there p = Ξ“ !! p infix 3 _⊒_∢_ data _⊒_∢_ : context β†’ CL β†’ type β†’ Set where ctx : βˆ€ {v : π“₯} {Ξ“ : context} β†’ (p : v βˆˆβ‚ Ξ“) β†’ -------------------- Ξ“ ⊒ ` v ∢ (Ξ“ !! p) k : βˆ€ {Ξ“ : context} {Οƒ Ο„ : type} β†’ -------------------- Ξ“ ⊒ K ∢ Οƒ β‡’ Ο„ β‡’ Οƒ s : βˆ€ {Ξ“ : context} {Οƒ Ο„ ρ : type} β†’ -------------------- Ξ“ ⊒ S ∢ (Οƒ β‡’ Ο„ β‡’ ρ) β‡’ (σ ⇒ Ο„) β‡’ Οƒ β‡’ ρ app : βˆ€ {Ξ“ : context} {M N : CL} {Οƒ Ο„ : type} β†’ Ξ“ ⊒ M ∢ Οƒ β‡’ Ο„ β†’ Ξ“ ⊒ N ∢ Οƒ β†’ -------------------- Ξ“ ⊒ M βˆ™ N ∢ Ο„ I-types : βˆ€ {Οƒ : type} β†’ [] ⊒ I ∢ Οƒ β‡’ Οƒ I-types = app (app s k) (k {Ο„ = ⋆}) B-types : βˆ€ {Οƒ Ο„ ρ : type} β†’ [] ⊒ B ∢ (Ο„ β‡’ ρ) β‡’ (Οƒ β‡’ Ο„) β‡’ (Οƒ β‡’ ρ) B-types = app (app s (app k s)) k W-types : βˆ€ {Οƒ Ο„ : type} β†’ [] ⊒ W ∢ (Οƒ β‡’ Οƒ β‡’ Ο„) β‡’ Οƒ β‡’ Ο„ W-types = app (app s s) (app k I-types) C-types : βˆ€ {Οƒ Ο„ ρ : type} β†’ [] ⊒ C ∢ (Οƒ β‡’ Ο„ β‡’ ρ) β‡’ Ο„ β‡’ Οƒ β‡’ ρ C-types = app (app s (app (app B-types B-types) s)) (app k k) M-does-not-type : βˆ€ {Οƒ : type} β†’ Β¬ ([] ⊒ M ∢ Οƒ) M-does-not-type (app (app s (app (app s k) k)) (app (app s ()) k))