Composite Data Types as Algebra, Logic Recursive Types

Algebraic Data Types

Christine Rizkallah CSE, UNSW (and data61) Term 3 2019

1 Classes Structs Unions Records

Composite Data Types as Algebra, Logic Recursive Types

Composite Data Types

Most of the types we have seen so far are basic types, in the sense that they represent built-in machine data representations. Real programming languages feature ways to compose types together to produce new types, such as:

2 Classes

Unions

Composite Data Types as Algebra, Logic Recursive Types

Composite Data Types

Most of the types we have seen so far are basic types, in the sense that they represent built-in machine data representations. Real programming languages feature ways to compose types together to produce new types, such as:

Tuples Structs

Records

3 Unions

Composite Data Types as Algebra, Logic Recursive Types

Composite Data Types

Most of the types we have seen so far are basic types, in the sense that they represent built-in machine data representations. Real programming languages feature ways to compose types together to produce new types, such as: Classes Tuples Structs

Records

4 Composite Data Types as Algebra, Logic Recursive Types

Composite Data Types

Most of the types we have seen so far are basic types, in the sense that they represent built-in machine data representations. Real programming languages feature ways to compose types together to produce new types, such as: Classes Tuples Structs Unions Records

5 Composite Data Types as Algebra, Logic Recursive Types

Combining values conjunctively We want to store two things in one value.

(might want to use non-compact slides for this one)

Haskell Tuples type Point=(Float, Float)

midpoint (x1,y1) (x2,y2) = ((x1+x2)/2, (y1+y2)/2)

6 Composite Data Types as Algebra, Logic Recursive Types

Combining values conjunctively We want to store two things in one value.

(might want to use non-compact slides for this one) Haskell Datatypes data Point= Pnt{x:: Float Haskell Tuples , y:: Float } type Point=(Float, Float) midpoint(Pnt x1 y1) (Pnt x2 y2) midpoint (x1,y1) (x2,y2) = ((x1+x2)/2, (y1+y2)/2) = ((x1+x2)/2, (y1+y2)/2) midpoint' p1 p2= = ((x p1+ x p2)/2, (y p1+ y p2)/2)

7 Composite Data Types as Algebra, Logic Recursive Types

Combining values conjunctively We want to store two things in one value.

(might want to use non-compact slides for this one) Haskell Datatypes C Structs data Point= typedef struct point { Pnt{x:: Float float x; Haskell Tuples , y:: Float float y; } type Point=}(Float point;, Float) point midPoint (point p1, point p2) { midpoint(Pnt x1 y1) (Pnt x2 y2) midpoint (x1,y1)point (x2,y2) mid; = ((x1+x2)/2, (y1+y2)/2) = ((x1+x2)/mid.x2, (y1= +(p1.xy2)/2+) p2.x)/ 2.0; mid.y= (p2.y+ p2.y)/ 2.0; midpoint' p1 p2= return mid; = ((x p1+ x p2)/2, } (y p1+ y p2)/2)

8 Composite Data Types as Algebra, Logic Recursive Types

Combining values conjunctively We want to store two things in one value.

(might want to use non-compact slides for this one) Haskell Datatypes C Structs data Point= typedef struct point {Java Pnt{x:: Float floatclass x; Point{ Haskell Tuples , y:: Float float y; public floatx; } type Point=}(Float point;public, Float float) y; point midPoint (point p1, point p2) { } midpoint(Pnt x1 y1) (Pnt x2 y2) midpoint (x1,y1)point (x2,y2) mid; Point midPoint(=Point ((x1+ p1x2), /Point2, (y1 p2+y2)){ /2) = ((x1+x2)/mid.x2, (y1Point= +(p1.xy2)/ mid2+) p2.x)= new /Point 2.0;(); mid.y= (p2.y+ p2.y)/ 2.0; mid.x=(p1.x+midpoint' p2.x)/ 2.0 p1; p2= return mid; mid.y=(p2.y+ =p2 ((x.y)/ p1 2.0+ x; p2)/2, } return mid; (y p1+ y p2)/2) }

9 Composite Data Types as Algebra, Logic Recursive Types

Combining values conjunctively We want to store two things in one value.

(might want to use non-compact slides for this one) Haskell Datatypes C Structs data Point= typedef struct point {Java Pnt“Better”{x:: Float Java floatclass x; Point{ Haskell Tuplesclass Point{ , y:: Float float y; publicprivate float floatx;; } type Point=}(Float point;public, Floatprivate float) floaty;; public Point(floatx, floaty){ point midPoint (point p1, point p2) { } this.x=x;midpoint this.y=y; (Pnt x1 y1) (Pnt x2 y2) midpoint (x1,y1)point (x2,y2) mid;} Point midPoint(=Point ((x1+ p1x2), /Point2, (y1 p2+y2)){ /2) = ((x1+x2)/2, (y1+publicy2)/2 float) getX(){return this.x;} mid.xPoint= (p1.xpublic mid +float p2.x)= new getY /Point ()2.0{return;(); this.y;} mid.y= (p2.ypublic +float p2.y) setX/ (2.0float;x){this.x=x;} mid.x=(p1.x+midpoint' p2.x)/ 2.0 p1; p2= returnmid mid;public.y=( p2float.y +setY p2(.floaty)/ y2.0){this; .y=y;} } = ((x p1+ x p2)/2, } returnPoint midPoint mid; (Point(y p1, p1 Point+ y p2) p2){/2) } return new Point((p1.getX()+ p2.getX())/ 2.0, (p2.getY()+ p2.getY())/ 2.0); } 10 Composite Data Types as Algebra, Logic Recursive Types

Product Types

In MinHS, we will have a very minimal way to accomplish this, called a product type:

τ1 × τ2

We won’t have type declarations, named fields or anything like that. More than two values can be combined by nesting products, for example a three dimensional vector:

Int × (Int × Int)

11 Composite Data Types as Algebra, Logic Recursive Types

Constructors and Eliminators

We can construct a product type similar to Haskell tuples:

Γ ` e1 : τ1 Γ ` e2 : τ2

Γ ` (e1, e2): τ1 × τ2

The only way to extract each component of the product is to use the fst and snd eliminators:

Γ ` e : τ1 × τ2 Γ ` e : τ1 × τ2

Γ ` fst e : τ1 Γ ` snd e : τ2

12 Composite Data Types as Algebra, Logic Recursive Types

Examples

Example (Midpoint) recfun midpoint :: ((Int × Int) → (Int × Int) → (Int × Int)) p1 = recfun midpoint0 :: ((Int × Int) → (Int × Int)) p2 = ((fst p1 + fst p2) ÷ 2, (snd p1 + snd p2) ÷ 2)

Example (Uncurried Division) recfun div :: ((Int × Int) → Int) args = if (fst args < snd args) then 0 else div (fst args − snd args, snd args)

13 Composite Data Types as Algebra, Logic Recursive Types

Dynamic Semantics

0 0 e1 7→M e1 e2 7→M e2 0 0 (e1, e2) 7→M (e1, e2) (v1, e2) 7→M (v1, e2)

e 7→ e0 e 7→ e0 0 0 fst e 7→M fst e snd e 7→M snd e

fst (v1, v2) 7→M v1 snd (v1, v2) 7→M v2

14 Composite Data Types as Algebra, Logic Recursive Types

Unit Types

Currently, we have no way to express a type with just one value. This may seem useless at first, but it becomes useful in combination with other types. We’ll introduce a type, 1, pronounced unit, that has exactly one inhabitant, written ():

Γ ` () : 1

15 In general we want to express data that can be one of multiple alternatives, that contain different of data. Example (More elaborate alternatives) type Length= Int type Angle= Int data Shape= Rect Length Length | Circle Length| Point | Triangle Angle Length Length

This is awkward in many languages. In Java we’d have to use inheritance. In C we’d have to use unions.

Composite Data Types as Algebra, Logic Recursive Types

Disjunctive Composition We can’t, with the types we have, express a type with exactly three values. Example (Trivalued type) data TrafficLight= Red| Amber| Green

16 Composite Data Types as Algebra, Logic Recursive Types

Disjunctive Composition We can’t, with the types we have, express a type with exactly three values. Example (Trivalued type) data TrafficLight= Red| Amber| Green

In general we want to express data that can be one of multiple alternatives, that contain different bits of data. Example (More elaborate alternatives) type Length= Int type Angle= Int data Shape= Rect Length Length | Circle Length| Point | Triangle Angle Length Length

This is awkward in many languages. In Java we’d have to use inheritance. In C we’d have to use unions. 17 Composite Data Types as Algebra, Logic Recursive Types

Sum Types

We will use sum types to express the possibility that data may be one of two forms.

τ1 + τ2

This is similar to the Haskell Either type. Our TrafficLight type can be expressed (grotesquely) as a sum of units: TrafficLight ' 1 + (1 + 1)

18 Composite Data Types as Algebra, Logic Recursive Types

Constructors and Eliminators for Sums

To make a value of type τ1 + τ2, we invoke one of two constructors:

Γ ` e : τ1 Γ ` e : τ2

Γ ` InL e : τ1 + τ2 Γ ` InR e : τ1 + τ2

We can branch based on which alternative is used using :

Γ ` e : τ1 + τ2 x : τ1, Γ ` e1 : τ y : τ2, Γ ` e2 : τ

Γ ` (case e of InL x → e1; InR y → e2): τ

(Using concrete syntax here, for readability.) (Feel free to replace it with abstract syntax of your choosing.)

19 Composite Data Types as Algebra, Logic Recursive Types

Examples

Example (Traffic Lights) Our traffic light type has three values as required:

TrafficLight ' 1 + (1 + 1)

Red ' InL () Amber ' InR (InL ()) Green ' InR (InR ())

20 Composite Data Types as Algebra, Logic Recursive Types

Examples We can convert most (non-recursive) Haskell types to equivalent MinHs types now. 1 Replace all constructors with 1 2 Add a × between all constructor arguments. 3 Change the | that separates constructors to a+. Example data Shape= Rect Length Length | Circle Length| Point | Triangle Angle Length Length '

1 × (Int × Int) + 1 × Int + 1 + 1 × (Int × (Int × Int))

21 Composite Data Types as Algebra, Logic Recursive Types

Dynamic Semantics

0 0 e 7→M e e 7→M e 0 0 InL e 7→M InL e InR e 7→M InR e

0 e 7→M e 0 (case e of InL x. e1; InR y. e2) 7→M (case e of InL x. e1; InR y. e2)

(case (InL v) of InL x. e1; InR y. e2) 7→M e1[x := v]

(case (InR v) of InL x. e1; InR y. e2) 7→M e2[y := v]

22 Composite Data Types as Algebra, Logic Recursive Types

Dynamic Semantics

0 0 e 7→M e e 7→M e 0 0 InL e 7→M InL e InR e 7→M InR e

(case (InL v) of InL x. e1; InR y. e2) 7→M e1[x := v]

(case (InR v) of InL x. e1; InR y. e2) 7→M e2[y := v]

0 e 7→M e 0 (case e of InL x. e1; InR y. e2) 7→M (case e of InL x. e1; InR y. e2)

23 Composite Data Types as Algebra, Logic Recursive Types

Dynamic Semantics

0 0 e 7→M e e 7→M e 0 0 InL e 7→M InL e InR e 7→M InR e

(case (InR v) of InL x. e1; InR y. e2) 7→M e2[y := v]

0 e 7→M e 0 (case e of InL x. e1; InR y. e2) 7→M (case e of InL x. e1; InR y. e2)

(case (InL v) of InL x. e1; InR y. e2) 7→M e1[x := v]

24 Composite Data Types as Algebra, Logic Recursive Types

Dynamic Semantics

0 0 e 7→M e e 7→M e 0 0 InL e 7→M InL e InR e 7→M InR e

0 e 7→M e 0 (case e of InL x. e1; InR y. e2) 7→M (case e of InL x. e1; InR y. e2)

(case (InL v) of InL x. e1; InR y. e2) 7→M e1[x := v]

(case (InR v) of InL x. e1; InR y. e2) 7→M e2[y := v]

25 Composite Data Types as Algebra, Logic Recursive Types

The Empty Type

We add another type, called 0, that has no inhabitants. Because it is empty, there is no way to construct it. We do have a way to eliminate it, however:

Γ ` e : 0 Γ ` absurd e :?

26 Composite Data Types as Algebra, Logic Recursive Types

The Empty Type

We add another type, called 0, that has no inhabitants. Because it is empty, there is no way to construct it. We do have a way to eliminate it, however:

Γ ` e : 0 Γ ` absurd e : τ

If I have a variable of the empty type in scope, we must be looking at an expression that will never be evaluated. Therefore, we can assign any type we like to this expression, because it will never be executed.

27 Identity: 0 + τ ' τ

Commutativity: τ1 + τ2 ' τ2 + τ1 Laws for( τ, ×, 1)

Associativity:( τ1 × τ2) × τ3 ' τ1 × (τ2 × τ3) Identity: 1 × τ ' τ

Commutativity: τ1 × τ2 ' τ2 × τ1 Combining × and+:

Distributivity: τ1 × (τ2 + τ3) ' (τ1 × τ2) + (τ1 × τ3) Absorption: 0 × τ ' 0 What does ' mean here?

Composite Data Types as Algebra, Logic Recursive Types

Semiring Structure These types we have defined form an algebraic structure called a commutative semiring. Laws for( τ, +, 0):

Associativity:( τ1 + τ2) + τ3 ' τ1 + (τ2 + τ3)

28 Commutativity: τ1 + τ2 ' τ2 + τ1 Laws for( τ, ×, 1)

Associativity:( τ1 × τ2) × τ3 ' τ1 × (τ2 × τ3) Identity: 1 × τ ' τ

Commutativity: τ1 × τ2 ' τ2 × τ1 Combining × and+:

Distributivity: τ1 × (τ2 + τ3) ' (τ1 × τ2) + (τ1 × τ3) Absorption: 0 × τ ' 0 What does ' mean here?

Composite Data Types as Algebra, Logic Recursive Types

Semiring Structure These types we have defined form an algebraic structure called a commutative semiring. Laws for( τ, +, 0):

Associativity:( τ1 + τ2) + τ3 ' τ1 + (τ2 + τ3) Identity: 0 + τ ' τ

29 Laws for( τ, ×, 1)

Associativity:( τ1 × τ2) × τ3 ' τ1 × (τ2 × τ3) Identity: 1 × τ ' τ

Commutativity: τ1 × τ2 ' τ2 × τ1 Combining × and+:

Distributivity: τ1 × (τ2 + τ3) ' (τ1 × τ2) + (τ1 × τ3) Absorption: 0 × τ ' 0 What does ' mean here?

Composite Data Types as Algebra, Logic Recursive Types

Semiring Structure These types we have defined form an algebraic structure called a commutative semiring. Laws for( τ, +, 0):

Associativity:( τ1 + τ2) + τ3 ' τ1 + (τ2 + τ3) Identity: 0 + τ ' τ

Commutativity: τ1 + τ2 ' τ2 + τ1

30 Identity: 1 × τ ' τ

Commutativity: τ1 × τ2 ' τ2 × τ1 Combining × and+:

Distributivity: τ1 × (τ2 + τ3) ' (τ1 × τ2) + (τ1 × τ3) Absorption: 0 × τ ' 0 What does ' mean here?

Composite Data Types as Algebra, Logic Recursive Types

Semiring Structure These types we have defined form an algebraic structure called a commutative semiring. Laws for( τ, +, 0):

Associativity:( τ1 + τ2) + τ3 ' τ1 + (τ2 + τ3) Identity: 0 + τ ' τ

Commutativity: τ1 + τ2 ' τ2 + τ1 Laws for( τ, ×, 1)

Associativity:( τ1 × τ2) × τ3 ' τ1 × (τ2 × τ3)

31 Commutativity: τ1 × τ2 ' τ2 × τ1 Combining × and+:

Distributivity: τ1 × (τ2 + τ3) ' (τ1 × τ2) + (τ1 × τ3) Absorption: 0 × τ ' 0 What does ' mean here?

Composite Data Types as Algebra, Logic Recursive Types

Semiring Structure These types we have defined form an algebraic structure called a commutative semiring. Laws for( τ, +, 0):

Associativity:( τ1 + τ2) + τ3 ' τ1 + (τ2 + τ3) Identity: 0 + τ ' τ

Commutativity: τ1 + τ2 ' τ2 + τ1 Laws for( τ, ×, 1)

Associativity:( τ1 × τ2) × τ3 ' τ1 × (τ2 × τ3) Identity: 1 × τ ' τ

32 Combining × and+:

Distributivity: τ1 × (τ2 + τ3) ' (τ1 × τ2) + (τ1 × τ3) Absorption: 0 × τ ' 0 What does ' mean here?

Composite Data Types as Algebra, Logic Recursive Types

Semiring Structure These types we have defined form an algebraic structure called a commutative semiring. Laws for( τ, +, 0):

Associativity:( τ1 + τ2) + τ3 ' τ1 + (τ2 + τ3) Identity: 0 + τ ' τ

Commutativity: τ1 + τ2 ' τ2 + τ1 Laws for( τ, ×, 1)

Associativity:( τ1 × τ2) × τ3 ' τ1 × (τ2 × τ3) Identity: 1 × τ ' τ

Commutativity: τ1 × τ2 ' τ2 × τ1

33 Absorption: 0 × τ ' 0 What does ' mean here?

Composite Data Types as Algebra, Logic Recursive Types

Semiring Structure These types we have defined form an algebraic structure called a commutative semiring. Laws for( τ, +, 0):

Associativity:( τ1 + τ2) + τ3 ' τ1 + (τ2 + τ3) Identity: 0 + τ ' τ

Commutativity: τ1 + τ2 ' τ2 + τ1 Laws for( τ, ×, 1)

Associativity:( τ1 × τ2) × τ3 ' τ1 × (τ2 × τ3) Identity: 1 × τ ' τ

Commutativity: τ1 × τ2 ' τ2 × τ1 Combining × and+:

Distributivity: τ1 × (τ2 + τ3) ' (τ1 × τ2) + (τ1 × τ3)

34 What does ' mean here?

Composite Data Types as Algebra, Logic Recursive Types

Semiring Structure These types we have defined form an algebraic structure called a commutative semiring. Laws for( τ, +, 0):

Associativity:( τ1 + τ2) + τ3 ' τ1 + (τ2 + τ3) Identity: 0 + τ ' τ

Commutativity: τ1 + τ2 ' τ2 + τ1 Laws for( τ, ×, 1)

Associativity:( τ1 × τ2) × τ3 ' τ1 × (τ2 × τ3) Identity: 1 × τ ' τ

Commutativity: τ1 × τ2 ' τ2 × τ1 Combining × and+:

Distributivity: τ1 × (τ2 + τ3) ' (τ1 × τ2) + (τ1 × τ3) Absorption: 0 × τ ' 0

35 Composite Data Types as Algebra, Logic Recursive Types

Semiring Structure These types we have defined form an algebraic structure called a commutative semiring. Laws for( τ, +, 0):

Associativity:( τ1 + τ2) + τ3 ' τ1 + (τ2 + τ3) Identity: 0 + τ ' τ

Commutativity: τ1 + τ2 ' τ2 + τ1 Laws for( τ, ×, 1)

Associativity:( τ1 × τ2) × τ3 ' τ1 × (τ2 × τ3) Identity: 1 × τ ' τ

Commutativity: τ1 × τ2 ' τ2 × τ1 Combining × and+:

Distributivity: τ1 × (τ2 + τ3) ' (τ1 × τ2) + (τ1 × τ3) Absorption: 0 × τ ' 0 What does ' mean here? 36 Composite Data Types as Algebra, Logic Recursive Types

Isomorphism

Two types τ1 and τ2 are isomorphic, written τ1 ' τ2, if there exists a bijection between them. This means that for each value in τ1 we can find a unique value in τ2 and vice versa. We can use isomorphisms to simplify our Shape type:

1 × (Int × Int) + 1 × Int + 1 + 1 × (Int × (Int × Int))

'

Int × Int + Int + 1 + Int × (Int × Int)

37 Composite Data Types as Algebra, Logic Recursive Types

Examining our Types Lets look at the rules for typed lambda calculus extended with sums and products:

Γ ` e : 0 Γ ` absurd e : τ Γ ` () : 1

Γ ` e : τ1 Γ ` e : τ2

Γ ` InL e : τ1 + τ2 Γ ` InR e : τ1 + τ2

Γ ` e : τ1 + τ2 x : τ1, Γ ` e1 : τ y : τ2, Γ ` e2 : τ

Γ ` (case e of InL x → e1; InR y → e2): τ

Γ ` e1 : τ1 Γ ` e2 : τ2 Γ ` e : τ1 × τ2 Γ ` e : τ1 × τ2

Γ ` (e1, e2): τ1 × τ2 Γ ` fst e : τ1 Γ ` snd e : τ2

Γ ` e1 : τ1 → τ2 Γ ` e2 : τ1 x : τ1, Γ ` e : τ2

Γ ` e1 e2 : τ2 Γ ` λx. e : τ1 → τ2

38 Composite Data Types as Algebra, Logic Recursive Types

Squinting a Little Lets remove all the terms, leaving just the types and the contexts:

Γ ` 0 Γ ` τ Γ ` 1

Γ ` τ1 Γ ` τ2

Γ ` τ1 + τ2 Γ ` τ1 + τ2

Γ ` τ1 + τ2 τ1, Γ ` τ τ2, Γ ` τ Γ ` τ

Γ ` τ1 Γ ` τ2 Γ ` τ1 × τ2 Γ ` τ1 × τ2

Γ ` τ1 × τ2 Γ ` τ1 Γ ` τ2

Γ ` τ1 → τ2 Γ ` τ1 τ1, Γ ` τ2

Γ ` τ2 Γ ` τ1 → τ2

Does this resemble anything you’ve seen before?

39 Composite Data Types as Algebra, Logic Recursive Types

A surprising coincidence! Types are exactly the same structure as constructive logic: Γ ` ⊥ Γ ` P Γ ` >

Γ ` P1 Γ ` P2

Γ ` P1 ∨ P2 Γ ` P1 ∨ P2

Γ ` P1 ∨ P2 P1, Γ ` PP2, Γ ` P Γ ` P

Γ ` P1 Γ ` P2 Γ ` P1 ∧ P2 Γ ` P1 ∧ P2

Γ ` P1 ∧ P2 Γ ` P1 Γ ` P2

Γ ` P1 → P2 Γ ` P1 P1, Γ ` P2

Γ ` P2 Γ ` P1 → P2 This means, if we can construct a program of a certain type, we have also created a constructive proof of a certain proposition. 40 It turns out, no matter what logic you want to define, there is always a corresponding λ-calculus, and vice versa. Constructive Logic Typed λ-Calculus Classical Logic Continuations Modal Logic Monads Linear Logic Linear Types, Session Types Separation Logic Region Types

Composite Data Types as Algebra, Logic Recursive Types

The Curry-Howard Isomorphism This correspondence goes by many names, but is usually attributed to Haskell Curry and William Howard. It is a very deep result: Programming Logic Types Propositions Programs Proofs Evaluation Proof Simplification

41 Composite Data Types as Algebra, Logic Recursive Types

The Curry-Howard Isomorphism This correspondence goes by many names, but is usually attributed to Haskell Curry and William Howard. It is a very deep result: Programming Logic Types Propositions Programs Proofs Evaluation Proof Simplification It turns out, no matter what logic you want to define, there is always a corresponding λ-calculus, and vice versa. Constructive Logic Typed λ-Calculus Classical Logic Continuations Modal Logic Monads Linear Logic Linear Types, Session Types Separation Logic Region Types

42 Example (Transitivity of Implication) transitive :: (A → B) → (B → C) → (A → C) transitive f g x = g (f x) Transitivity of implication is just function composition.

Composite Data Types as Algebra, Logic Recursive Types

Examples

Example (Commutativity of Conjunction) andComm :: A × B → B × A andComm p = (snd p, fst p) This proves A ∧ B → B ∧ A.

43 Composite Data Types as Algebra, Logic Recursive Types

Examples

Example (Commutativity of Conjunction) andComm :: A × B → B × A andComm p = (snd p, fst p) This proves A ∧ B → B ∧ A.

Example (Transitivity of Implication) transitive :: (A → B) → (B → C) → (A → C) transitive f g x = g (f x) Transitivity of implication is just function composition.

44 Composite Data Types as Algebra, Logic Recursive Types

Caveats All functions we define have to be total and terminating. Otherwise we get an inconsistent logic that lets us prove false things: proof 1 :: P = NP proof 1 = proof 1

proof 2 :: P 6= NP proof 2 = proof 2

Most common calculi correspond to constructive logic, not classical ones, so principles like the law of excluded middle or double negation elimination do not hold:

¬¬P → P

45 We need a way to do recursion!

Composite Data Types as Algebra, Logic Recursive Types

Inductive Structures

What about types like lists? data IntList= Nil| Int IntList We can’t express these in MinHS yet:

1 + (Int×??)

46 Composite Data Types as Algebra, Logic Recursive Types

Inductive Structures

What about types like lists? data IntList= Nil| Cons Int IntList We can’t express these in MinHS yet:

1 + (Int×??)

We need a way to do recursion!

47 ' 1 + (Int × (rec t. 1 + (Int × t))) ' 1 + (Int × (1 + (Int × (rec t. 1 + (Int × t))))) '···

Composite Data Types as Algebra, Logic Recursive Types

Recursive Types

We introduce a new form of type, written rec t. τ, that allows us to refer to the entire type:

IntList ' rec t. 1 + (Int × t)

48 ' 1 + (Int × (1 + (Int × (rec t. 1 + (Int × t))))) '···

Composite Data Types as Algebra, Logic Recursive Types

Recursive Types

We introduce a new form of type, written rec t. τ, that allows us to refer to the entire type:

IntList ' rec t. 1 + (Int × t) ' 1 + (Int × (rec t. 1 + (Int × t)))

49 Composite Data Types as Algebra, Logic Recursive Types

Recursive Types

We introduce a new form of type, written rec t. τ, that allows us to refer to the entire type:

IntList ' rec t. 1 + (Int × t) ' 1 + (Int × (rec t. 1 + (Int × t))) ' 1 + (Int × (1 + (Int × (rec t. 1 + (Int × t))))) '···

50 Composite Data Types as Algebra, Logic Recursive Types

Typing Rules

We construct a recursive type with roll, and unpack the recursion one level with unroll:

?? Γ ` roll e : rec t. τ

51 Composite Data Types as Algebra, Logic Recursive Types

Typing Rules

We construct a recursive type with roll, and unpack the recursion one level with unroll:

Γ ` e : τ[t := rec t. τ] Γ ` roll e : rec t. τ

52 Composite Data Types as Algebra, Logic Recursive Types

Typing Rules

We construct a recursive type with roll, and unpack the recursion one level with unroll:

Γ ` e : τ[t := rec t. τ] Γ ` roll e : rec t. τ

Γ ` e : rec t. τ Γ ` unroll e : τ[t := rec t. τ]

53 roll (InL ()) [1]= roll (InR (1, roll (InL ()))) [1, 2]= roll (InR (1, roll (InR (2, roll (InL ())))))

Composite Data Types as Algebra, Logic Recursive Types

Example

Example Take our IntList example:

rec t. 1 + (Int × t)

[]=

54 roll (InR (1, roll (InL ()))) [1, 2]= roll (InR (1, roll (InR (2, roll (InL ())))))

Composite Data Types as Algebra, Logic Recursive Types

Example

Example Take our IntList example:

rec t. 1 + (Int × t)

[]= roll (InL ()) [1]=

55 roll (InR (1, roll (InR (2, roll (InL ())))))

Composite Data Types as Algebra, Logic Recursive Types

Example

Example Take our IntList example:

rec t. 1 + (Int × t)

[]= roll (InL ()) [1]= roll (InR (1, roll (InL ()))) [1, 2]=

56 Composite Data Types as Algebra, Logic Recursive Types

Example

Example Take our IntList example:

rec t. 1 + (Int × t)

[]= roll (InL ()) [1]= roll (InR (1, roll (InL ()))) [1, 2]= roll (InR (1, roll (InR (2, roll (InL ())))))

57 Composite Data Types as Algebra, Logic Recursive Types

Dynamic Semantics

Nothing interesting here:

0 0 e 7→M e e 7→M e 0 0 roll e 7→M roll e unroll e 7→M unroll e

unroll (roll e) 7→M e

58