| name | dependent-type-implementer |
| description | Implements dependently typed lambda calculus (Pi types). Use when: (1) Building proof assistants, (2) Formalizing mathematics, (3) Verified programming. |
| version | 1.0.0 |
| tags | ["type-systems","dependent-types","type-theory","proofs"] |
| difficulty | advanced |
| languages | ["python","agda","idris"] |
| dependencies | ["simply-typed-lambda-calculus"] |
Dependent Type Implementer
Implements dependent type theory (Type Theory, Π Types, Σ Types).
When to Use
- Building proof assistants (Coq, Agda, Idris)
- Formalizing mathematics
- Verified programming
- Type-level computation
What This Skill Does
- Implements Π types - Dependent functions τ → σ(x)
- Implements Σ types - Dependent pairs (x:τ) × σ(x)
- Type checking - With conversion and unification
- Proof elaboration - From surface to core syntax
How to Use
- Start from a minimal core (
Var, Pi, Lam, App, universes)
- Implement normalization and definitional equality
- Type-check by synthesis/checking with conversion
- Add
Sigma, naturals, and eliminators incrementally
Core Theory
Dependent Function (Π):
Π(x:A). B or (x:A) → B
When x not in B: A → B (non-dependent)
Dependent Pair (Σ):
Σ(x:A). B or (x:A) × B
When x not in B: A × B (product)
Type formation rules:
Γ ⊢ A : s Γ, x:A ⊢ B : s
------------------------------
Γ ⊢ Π(x:A).B : s
Γ ⊢ A : s Γ, x:A ⊢ B : s
------------------------------
Γ ⊢ Σ(x:A).B : s
Implementation
(* Core Syntax (conceptual) *)
Term types:
- Type (universe)
- Var (de Bruijn index)
- Lam (abstraction with optional type annotation)
- App (application)
- Pi (dependent function type)
- Sigma (dependent pair type)
- Pair, Proj1, Proj2 (pair intro/elim)
- Unit, Nat, Zero, Succ, NatElim (basic types)
Type formation rules:
Γ ⊢ A : s Γ, x:A ⊢ B : s
------------------------------
Γ ⊢ Π(x:A).B : s
Γ ⊢ A : s Γ, x:A ⊢ B : s
------------------------------
Γ ⊢ Σ(x:A).B : s
Typing rules (key cases):
T_Abs: Γ ⊢ A : s
Γ, x:A ⊢ N : B
----------------
Γ ⊢ λx:A. N : Π(x:A).B
T_App: Γ ⊢ M : Π(x:A).B
Γ ⊢ N : A
-----------------
Γ ⊢ M N : B[x := N]
T_Pair: Γ ⊢ M : A
Γ ⊢ N : B[x := M]
------------------
Γ ⊢ (M, N) : Σ(x:A).B
Elaboration
From surface syntax to core:
Surface: λ(x : A) => e
Core: Lam A e
Elaboration algorithm:
1. Infer type of binding: A : s
2. Extend context with x : A
3. Elaborate body: e : B
4. Compute result type:
- Non-dependent: Pi A (λx. B)
- Dependent: Pi A (λx. B)
Pattern matching elaboration:
match e return P with
| c1 => e1
| c2 => e2
end
becomes:
NatElim P e (λ_. e1) (λn. λIH. e2)
Universe Polymorphism
(* Cumulative universes *)
Inductive universe : Type :=
| Set0 : universe
| Set1 : universe
| Set2 : universe
| ... (* Prop, SProp, etc. *)
(* Universe constraints *)
Check (Type@{i} -> Type@{j}).
(* i ≤ j required *)
(* Cumulative: Set@{i} ≤ Set@{i+1} *)
Implementation in OCaml
(* Core dependent type checker *)
type term =
| Var of int
| Lambda of term * term
| App of term * term
| Pi of term * term (* Π x : A. B *)
| Sigma of term * term (* Σ x : A. B *)
| Pair of term * term
| Proj1 of term
| Proj2 of term
| Star (* unit *)
| Nat | Zero | Succ of term
| NatElim of term * term * term * term
type value =
| VLambda of (value -> value)
| VPi of value * (value -> value)
| VSigma of value * value
| VPair of value * value
| VStar
| VNat
| VZero
| VSucc of value
let rec eval (t : term) (ρ : value list) : value =
match t with
| Var i -> List.nth ρ i
| Lambda (a, b) -> VLambda (fun v -> eval b (v :: ρ))
| App (m, n) ->
let vm = eval m ρ in
let vn = eval n ρ in
(match vm with
| VLambda f -> f vn
| _ -> failwith "apply non-function")
| Pi (a, b) -> VPi (eval a ρ) (fun v -> eval b (v :: ρ))
(* ... more cases *)
Key Concepts
| Concept | Description |
|---|
| Π types | Dependent functions |
| Σ types | Dependent pairs |
| Universes | Type of types (Set, Type₀, ...) |
| Conversion | βη-equivalence |
| Elaboration | Surface → core |
Advanced Features
| Feature | Description |
|---|
| Match | Pattern matching (via NatElim) |
| Universe polymorphism | Generic over universes |
| Cumulativity | Subtyping between universes |
| Irrelevance | Prop irrelevance (SProp) |
| Observational equality | UIP, univalence |
Tips
- Start with simple dependent types
- Implement conversion checking carefully
- Use de Bruijn for binding
- Consider universe constraints
- Handle definitional equality
Related Skills
system-f - Polymorphic lambda calculus
type-inference-engine - HM inference
coq-proof-assistant - Coq proofs
Canonical References
| Reference | Why It Matters |
|---|
| Coq Reference Manual | Definitive implementation reference |
| Martin-Löf, "Intuitionistic Type Theory" (1984) | Original dependent type theory |
| Harper & Pfenning, "On Equivalence and Canonical Forms in the LF Type Theory" (2005) | Type-directed conversion checking |
| Abel, Coquand & Dybjer, "Normalization by Evaluation for Martin-Löf Type Theory" (2007) | NbE for dependent types |
| Chapman, Altenkirch & McBride, "Epigram Reloaded: A Standalone Typechecker for ETT" (2006) | Elaboration implementation |
Tradeoffs and Limitations
Implementation Approach Tradeoffs
| Approach | Pros | Cons |
|---|
| Type checking | Decidable, simple | Less powerful inference |
| Type inference | More convenient | Complex constraint solving |
| Bidirectional | Balanced | Still incomplete |
When NOT to Implement Dependent Types
- For simple verification: Use refinement types instead (Liquid Haskell, F*)
- For performance: Consider Haskell/OCaml with GADTs
- For teaching: Start with System F or STLC
Complexity Considerations
- Undecidability: Full type checking is undecidable for dependent types
- Universe constraints: Solving universe constraints is complex
- Normalization: Required for conversion; expensive without NbE
- Type inference: Principally undecidable; use bidirectional checking
Limitations
- Performance: 10-100x slower than simple types
- Error messages: Hard to make comprehensible
- Termination checking: Required for soundness (or positivity)
- Universe levels: Must handle Level → Level max → etc.
- Normalization: Full β-reduction needed for conversion
- Learning curve: Users need to understand type theory
Research Tools & Artifacts
Dependent type systems:
| System | Language | What to Learn |
|---|
| Coq | OCaml | Production proof assistant |
| Agda | Haskell | Dependently typed programming |
| Idris | Idris | Type-driven development |
| Lean | Lean | Modern proof assistant |
| NuPRL | Lisp | Constructive type theory |
Key Papers
- Martin-Löf - Original type theory
- Coquand - Calculus of Constructions
- Harper et al. - Syntactic theory
Research Frontiers
1. Homotopy Type Theory
- Goal: Univalence, higher inductive types
- Approach: Path types, identity types
- Books: HoTT Book
2. Cubical Type Theory
- Goal: Computational univalence
- Approach: Kan operations, faces
Implementation Pitfalls
| Pitfall | Real Consequence | Solution |
|---|
| Universe inconsistency | Paradoxes | Universe checking |
| Non-termination | Unsoundness | Termination check |
| Conversion inefficiency | Slow checking | NbE |