All Projects → zehaochen19 → vanilla-lang

zehaochen19 / vanilla-lang

Licence: AGPL-3.0 license
An implementation of a predicative polymorphic language with bidirectional type inference and algebraic data types

Programming Languages

haskell
3896 projects
Nix
1067 projects

Projects that are alternatives of or similar to vanilla-lang

system-F
Formalization of the polymorphic lambda calculus and its parametricity theorem
Stars: ✭ 20 (-72.6%)
Mutual labels:  lambda-calculus, polymorphism, system-f
Write You A Haskell
Building a modern functional compiler from first principles. (http://dev.stephendiehl.com/fun/)
Stars: ✭ 3,064 (+4097.26%)
Mutual labels:  lambda-calculus, type-inference
Zion
A statically-typed strictly-evaluated garbage-collected readable programming language.
Stars: ✭ 33 (-54.79%)
Mutual labels:  lambda-calculus, polymorphism
Type-Theory
Lecture note on Lambda Calculus and Types for FLOLAC
Stars: ✭ 26 (-64.38%)
Mutual labels:  lambda-calculus, system-f
lambda-calculus
An introduction to the Lambda Calculus
Stars: ✭ 59 (-19.18%)
Mutual labels:  lambda-calculus, system-f
lambda-zero
A minimalist pure lazy functional programming language
Stars: ✭ 65 (-10.96%)
Mutual labels:  lambda-calculus
Java-Programs
Java Practiced Problems including concepts of OOPS, Interface, String , Collection.
Stars: ✭ 51 (-30.14%)
Mutual labels:  polymorphism
BOHM1.1
Bologna Optimal Higher-Order Machine, Version 1.1
Stars: ✭ 45 (-38.36%)
Mutual labels:  lambda-calculus
typeclass-interface-pattern
Ideas, thoughts, and notes on a typeclass/interface based polymorphism pattern for standard C
Stars: ✭ 26 (-64.38%)
Mutual labels:  polymorphism
lambda
Macro Lambda Calculus
Stars: ✭ 38 (-47.95%)
Mutual labels:  lambda-calculus
ftor
ftor enables ML-like type-directed, functional programming with Javascript including reasonable debugging.
Stars: ✭ 44 (-39.73%)
Mutual labels:  polymorphism
pomagma
An inference engine for extensional untyped λ-calculus
Stars: ✭ 15 (-79.45%)
Mutual labels:  lambda-calculus
gidti
Book: Gentle Introduction to Dependent Types with Idris
Stars: ✭ 70 (-4.11%)
Mutual labels:  lambda-calculus
meta-cedille
Minimalistic dependent type theory with syntactic metaprogramming
Stars: ✭ 40 (-45.21%)
Mutual labels:  lambda-calculus
js-church-encoding
Church Encoding Implementation in JavaScript
Stars: ✭ 33 (-54.79%)
Mutual labels:  lambda-calculus
swagger-object-validator
Node-Module to validate your model against a swagger spec and receive in-depth error traces
Stars: ✭ 27 (-63.01%)
Mutual labels:  polymorphism
StepULC
Efficient and single-steppable ULC evaluation algorithm
Stars: ✭ 15 (-79.45%)
Mutual labels:  lambda-calculus
poly collection
Fast containers of polymorphic objects.
Stars: ✭ 58 (-20.55%)
Mutual labels:  polymorphism
lambda-notebook
Lambda Notebook: Formal Semantics in Jupyter
Stars: ✭ 16 (-78.08%)
Mutual labels:  lambda-calculus
universe-of-syntax
A universe of scope- and type-safe syntaxes (syntices?). Includes generic implementation of type-preserving renaming/substitution with all the proofs you could possibly need.
Stars: ✭ 16 (-78.08%)
Mutual labels:  lambda-calculus

Vinilla Lang

Vanilla is a pure functional programming language based on System F, a classic but powerful type system.

Merits

Simple as it is, Vanilla contains many features that most main-stream languages don't have:

  • Higher-rank polymorphism
    • It allows using polymorphic functions as arguments of higher-order functions
  • Strong type inference
    • Only polymorphic and recursive bindings need annotations
  • Algebraic data types
  • Simplicity
    • Only foralls and arrows are built-in types
    • All regular types such as Unit and Bool can be declared as ADT and eliminated by case expression

Defects

  • No module system
  • For simplicity, this programming language only supports type checking and evaluation on closed terms.

Grammar

Types           A, B, C   ::= T A1...An | a | ∀a.A | A → B
Monotypes       τ, σ      ::= T τ1...τn | a | τ → σ

Data Type       T         ::= T
Constructor     K         ::= K
Declaration     D         ::= data T a1...at = K1 τ1...τm | ... | Kn σ1...σn .
Pattern         p         ::= K x1...xn

Expressions     e, f      ::=   x                                     -- variable
                              | K                                     -- constructor
                              | case e of {pi → ei}                   -- case
                              | λx.e                                  -- implicit λ
                              | λx : A.e                              -- annotated λ
                              | e1 e2                                 -- application
                              | e : A                                 -- annotation
                              | let x = e1 in e2                      -- let binding
                              | let x : A = e1 in e2                  -- annotated let binding
                              | let rec f : A = e1 in e2              -- recursive binding (sugar)
                              | fix e                                 -- fixpoint
                              | e @ A                                 -- type application

Program         P         ::= D P | e

A valid Vanilla program consists of several ADT declarations followed by a main expression.

ADT declarations are similar to ones in Haskell, except that they end with a dot for easy parsing.

Haskell-style comments (-- and {- -}) are also supported.

Usage

First of all, ghc and cabal-install should be installed in your $PATH

Examples

Higher-rank Polymorphism

Given example/cont.vn:

data Unit = Unit.

-- Can you belive that
-- type `a` and `∀r. ((a → r) → r)` are isomorphic?

let cont : ∀a. a → ∀r. ((a → r) → r) =
  λ x . λ callback . callback x
in

let runCont : ∀a. (∀r. (a → r) → r) → a =
  λ f . (let callback = λ x . x in f callback)
in

-- should output Unit
runCont (cont Unit)

Run

cabal run example/cont.vn

It should output:

Type:
Unit

Result:
Unit

Map for Lists

Given example/map.vn:

data Bool = False | True.
data List a = Nil | Cons a (List a).


let rec map : ∀a. ∀b. (a → b) → (List a) → (List b) =
  λ f. λ xs. case xs of {
      Nil → Nil,
      Cons y ys → Cons (f y) (map f ys)
    }
in

let not : Bool → Bool =
  λb. case b of {False → True, True → False}
in

let xs = Cons True (Cons False Nil) in

map not xs

Run

$ cabal run example/map.vn

It should output:

Type:
List Bool

Result:
Cons False (Cons True Nil)

Add operator for Natural Numbers

Given example/add.vn:

data Nat = Zero | Succ Nat.
data Prod a b = Prod a b.

-- add can be defined by `fixpoint`
let add : Nat → Nat → Nat =
  fix (λf. λx : Nat . λy : Nat. case x of {Zero → y, Succ a → Succ (f a y)})
in

-- or `let rec`
let rec add2 : Nat → Nat → Nat =
  λ x . λ y . case x of {Zero → y, Succ a → Succ (add2 a y)}
in

let two = Succ (Succ Zero) in
let three = Succ two in

-- 3 + 2 = 5
Prod (add three two) (add2 three two)

Run

$ cabal run example/add.vn

It should output the inferred type and evaluated value of this program:

Type:
Prod Nat Nat

Result:
Prod (Succ (Succ (Succ (Succ (Succ Zero))))) (Succ (Succ (Succ (Succ (Succ Zero)))))

Mutual Recursion

Mutual recursive functions can be easily defined with the fixpoint and projections.

Given example/evenodd.vn:

data Nat = Zero | Succ Nat.
data Bool = False | True.
data Prod a b = Prod a b.

let evenodd : Prod (Nat → Bool) (Nat → Bool) =
  fix (λ eo .
    let e = λ n : Nat . case n of { Zero → True, Succ x → (case eo of {Prod e o → o}) x } in
    let o = λ n : Nat . case n of { Zero → False, Succ x → (case eo of {Prod e o → e}) x } in
    (Prod e o))
in

let even = (case evenodd of {Prod e o → e}) in
let odd = (case evenodd of {Prod e o → o}) in

let five = Succ(Succ(Succ(Succ(Succ(Zero))))) in

Prod (even five) (odd five)

It reports:

Type:
Prod Bool Bool

Result:
Prod False True

Ill-typed Program

Given example/illtypedid.vn:

let id : Nat → Nat =
  (λx . x)
in
  id ()

It reports typechecking error:

Typecheck error:
cannot establish subtyping with Unit <: Nat

Unit tests

$ cabal test
...
Running 1 test suites...
Test suite vanilla-test: RUNNING...
Test suite vanilla-test: PASS
...

Features

  • Static semantic
  • Higher-rank polymorphism
  • Type inference
  • Dynamic semantic
  • Both annotated and implicit λ
  • Examples
  • Unit tests
  • Let Binding
  • Algebraic data types
    • Declarations
    • Introductions and eliminations
    • Well-formedness checking
  • Type application
  • Fixpoint for general recursion
  • Let rec
  • Parser
  • Pretty printing

References

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].