1
Programming Languages and Compilers (CS 421)
Based heavily on slides by Elsa Gunter, which were based in part on slides by Mattox Beckman, as updated by Vikram Adve and Gul Agha
Objectives for Today
2
Objectives for Today
3
4
Questions from last week?
5
Mutually Recursive Datatypes
Mutually Recursive Types
type 'a tree =
TreeLeaf of 'a | TreeNode of 'a treeList
and 'a treeList =
Last of 'a tree | More of ('a tree * 'a treeList)
*
6
Mutually Recursive Datatypes
Mutually Recursive Types
type 'a tree =
TreeLeaf of 'a | TreeNode of 'a treeList
and 'a treeList =
Last of 'a tree | More of ('a tree * 'a treeList)
*
7
Mutually Recursive Datatypes
Mutually Recursive Types
type 'a tree =
TreeLeaf of 'a | TreeNode of 'a treeList
and 'a treeList =
Last of 'a tree | More of ('a tree * 'a treeList)
*
8
Mutually Recursive Datatypes
Mutually Recursive Types
type 'a tree =
TreeLeaf of 'a | TreeNode of 'a treeList
and 'a treeList =
Last of 'a tree | More of ('a tree * 'a treeList)
*
9
Mutually Recursive Datatypes
Mutually Recursive Types
type 'a tree =
TreeLeaf of 'a | TreeNode of 'a treeList
and 'a treeList =
Last of 'a tree | More of ('a tree * 'a treeList)
*
10
Mutually Recursive Datatypes
Mutually Recursive Types
type 'a tree =
TreeLeaf of 'a | TreeNode of 'a treeList
and 'a treeList =
Last of 'a tree | More of ('a tree * 'a treeList)
*
11
Mutually Recursive Datatypes
Mutually Recursive Types
type 'a tree =
TreeLeaf of 'a | TreeNode of 'a treeList
and 'a treeList =
Last of 'a tree | More of ('a tree * 'a treeList)
*
12
Mutually Recursive Datatypes
Mutually Recursive Types
type 'a tree =
TreeLeaf of 'a | TreeNode of 'a treeList
and 'a treeList =
Last of 'a tree | More of ('a tree * 'a treeList)
*
13
Mutually Recursive Datatypes
Mutually Recursive Types - Values
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7))))))
5 7
3 2
*
14
Mutually Recursive Datatypes
Mutually Recursive Types - Values
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
5 7
3 2
*
15
Mutually Recursive Datatypes
Mutually Recursive Types - Values
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
5 7
3 2
*
16
Mutually Recursive Datatypes
Mutually Recursive Types - Values
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
5 7
3 2
*
17
Mutually Recursive Datatypes
Mutually Recursive Types - Values
5 7
3 2
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
*
18
Mutually Recursive Datatypes
Mutually Recursive Types - Values
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
5 7
3 2
*
19
Mutually Recursive Datatypes
Mutually Recursive Types - Values
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
5 7
3 2
*
20
Mutually Recursive Datatypes
Mutually Recursive Types - Values
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
5 7
3 2
*
21
Mutually Recursive Datatypes
Mutually Recursive Types - Values
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
5 7
3 2
*
22
Mutually Recursive Datatypes
Mutually Recursive Types - Values
TreeNode
More More Last
TreeLeaf TreeNode TreeLeaf
5 More Last 7
TreeLeaf TreeLeaf
3 2
*
23
Mutually Recursive Datatypes
Mutually Recursive Functions
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
5 7
3 2
*
24
Mutually Recursive Datatypes
Mutually Recursive Functions
TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
5 7
3 2
*
25
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
26
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
27
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
28
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
29
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
30
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
31
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
32
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
33
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
34
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
35
Mutually Recursive Datatypes
Mutually Recursive Functions
let rec fringe tree =
match tree with
| TreeLeaf x -> [x]
| TreeNode list -> list_fringe list
and list_fringe tree_list =
match tree_list with
| Last tree -> fringe tree
| More (tree, list) ->
(fringe tree) @ (list_fringe list)
*
36
Mutually Recursive Datatypes
Mutually Recursive Functions
5 7
3 2
# let tree = TreeNode
(More (TreeLeaf 5,
(More
(TreeNode (More (TreeLeaf 3, Last (TreeLeaf 2))),
Last (TreeLeaf 7)))))
in fringe tree;;
*
37
Mutually Recursive Datatypes
38
Questions so far?
39
Nested Recursive Datatypes
Nested Recursive Types
(* Alt. def, allowing empty lists & values anywhere *)
type 'a labeled_tree =
TreeNode of ('a * 'a labeled_tree list);;
*
40
Nested Recursive Datatypes
Nested Recursive Types - Values
(* Alt. def, allowing empty lists & values anywhere *)
type 'a labeled_tree =
TreeNode of ('a * 'a labeled_tree list);;
TreeNode
(5,
[TreeNode (3, []);
TreeNode
(2, [TreeNode (1, []); TreeNode (7, [])]);
TreeNode (5, [])])
*
41
Nested Recursive Datatypes
Nested Recursive Types - Values
(* A simpler definition, allowing empty lists *)
type 'a labeled_tree =
TreeNode of ('a * 'a labeled_tree list);;
TreeNode
(5,
[TreeNode (3, []);
TreeNode
(2, [TreeNode (1, []); TreeNode (7, [])]);
TreeNode (5, [])])
5
3 2 5
1 7
*
42
Nested Recursive Datatypes
Nested Recursive Types - Values
ltree = TreeNode(5)
:: :: :: [ ]
TreeNode(3) TreeNode(2) TreeNode(5)
[ ] :: :: [ ] [ ]
TreeNode(1) TreeNode(7)
[ ] [ ]
*
43
Nested Recursive Datatypes
Mutually Recursive Functions
let rec flatten_tree labtree =
match labtree with
| TreeNode (x, ts) -> x :: flatten_tree_list ts
and flatten_tree_list ts =
match ts with
| [] -> []
| labtree :: labtrees ->
flatten_tree labtree @ flatten_tree_list labtrees
*
44
Nested Recursive Datatypes
Mutually Recursive Functions
let rec flatten_tree labtree =
match labtree with
| TreeNode (x, ts) -> x :: flatten_tree_list ts
and flatten_tree_list ts =
match ts with
| [] -> []
| labtree :: labtrees ->
flatten_tree labtree @ flatten_tree_list labtrees
*
45
Nested recursive types lead to
mutually recursive functions!
Nested Recursive Datatypes
Mutually Recursive Functions
let rec flatten_tree labtree =
match labtree with
| TreeNode (x, ts) -> x :: flatten_tree_list ts
and flatten_tree_list ts =
match ts with
| [] -> []
| labtree :: labtrees ->
flatten_tree labtree @ flatten_tree_list labtrees
*
46
Nested recursive types lead to
mutually recursive functions!
Nested Recursive Datatypes
Can get around if clever, but nontrivial.
Mutually Recursive Functions
let rec flatten_tree labtree =
match labtree with
| TreeNode (x, ts) -> x :: flatten_tree_list ts
and flatten_tree_list ts =
match ts with
| [] -> []
| labtree :: labtrees ->
flatten_tree labtree @ flatten_tree_list labtrees
*
47
Nested recursive types lead to
mutually recursive functions!
Nested Recursive Datatypes
And we need polymorphism to work around!
48
Types and Type Checking
49
Questions so far?
Why Types?
*
50
Types and Type Checking
No Really, Why Types?
*
51
Types and Type Checking
Terminology
*
52
Types and Type Checking
Terminology
*
53
Types and Type Checking
Types as Specifications
*
54
Types and Type Checking
Sound Type System
*
55
Types and Type Checking
Strongly Typed Language
*
56
Types and Type Checking
Strongly Typed Language
*
57
Types and Type Checking
Static vs. Dynamic Types
*
58
Types and Type Checking
Static vs. Dynamic Types
*
59
Gradual types are not explicitly covered in class
Types and Type Checking
Type Checking
*
60
Types and Type Checking
Type Checking
*
61
Types and Type Checking
Type Declarations & Type Inference
*
62
63
Questions so far?
64
Types and Type Checking
Type Checking
*
65
Types and Type Checking
Type Checking
*
66
Types and Type Checking
Dynamic Type Checking
*
67
Types and Type Checking
Dynamic Type Checking
*
68
Types and Type Checking
Static Type Checking
*
69
Types and Type Checking
Static Type Checking
*
70
Types and Type Checking
Static Type Checking
*
71
Types and Type Checking
Static Type Checking
*
72
Dependent types are not explicitly covered in class, but I’m obsessed with them, so please ask in office hours or something
Types and Type Checking
Static Type Checking
*
73
Types and Type Checking
74
Type Judgments
Format of Type Judgments
*
75
Type Judgments
Format of Type Judgments
*
76
Type Judgments
Format of Type Judgments
*
77
Type Judgments
Format of Type Judgments
*
78
Type Judgments
Axioms – Constants (Monomorphic)
Γ ⊢ n : int (assuming n is an integer constant)
Γ ⊢ true : bool Γ ⊢ false : bool
*
79
Type Judgments
Axioms – Variables (Monomorphic Rule)
Notation: Let Γ(v) = T if v : T ∈ Γ
Note: if such T exits, its unique
Variable axiom:
Γ ⊢ v : T if Γ(v) = T
*
80
Type Judgments
Simple Rules – Arithmetic (Mono)
Primitive Binary operators (⊕ ∈ { +, -, *, …}):
Γ ⊢ t1: T1 Γ ⊢ t2: τ2 (⊕) : T1 → T2 → T3
Γ ⊢ t1 ⊕ t2 : T3
Special case: Relations (~ ∈ { < , > , =, <=, >= }):
Γ ⊢ t1 : T Γ ⊢ t2 : T (~) : T → T → bool
Γ ⊢ t1 ~ t2 :bool
For the moment, think T is int
*
81
Type Judgments
Simple Rules – Arithmetic (Mono)
Primitive Binary operators (⊕ ∈ { +, -, *, …}):
Γ ⊢ t1: T1 Γ ⊢ t2: τ2 (⊕) : T1 → T2 → T3
Γ ⊢ t1 ⊕ t2 : T3
Special case: Relations (~ ∈ { < , > , =, <=, >= }):
Γ ⊢ t1 : T Γ ⊢ t2 : T (~) : T → T → bool
Γ ⊢ t1 ~ t2 :bool
For the moment, think T is int
*
82
Type Judgments
Simple Rules – Arithmetic (Mono)
Primitive Binary operators (⊕ ∈ { +, -, *, …}):
Γ ⊢ t1: T1 Γ ⊢ t2: τ2 (⊕) : T1 → T2 → T3
Γ ⊢ t1 ⊕ t2 : T3
Special case: Relations (~ ∈ { < , > , =, <=, >= }):
Γ ⊢ t1 : T Γ ⊢ t2 : T (~) : T → T → bool
Γ ⊢ t1 ~ t2 :bool
For the moment, think T is int
*
83
Type Judgments
Example: { x : int } ⊢ x + 2 = 3 : bool
???
{x : int} ⊢ x + 2 = 3 : bool
*
84
What do we need to show first?
Bin
Type Judgments
Example: { x : int } ⊢ x + 2 = 3 : bool
{x : int} ⊢ x + 2 : int {x : int} ⊢ 3 : int
{x : int} ⊢ x + 2 = 3 : bool
*
85
What do we need to show first?
Bin
Bin
Type Judgments
Example: { x : int } ⊢ x + 2 = 3 : bool
???
{x : int} ⊢ x + 2 : int {x : int} ⊢ 3 : int
{x : int} ⊢ x + 2 = 3 : bool
*
86
Left-hand side?
Bin
Bin
Type Judgments
Example: { x : int } ⊢ x + 2 = 3 : bool
{x : int} ⊢ x : int {x : int} ⊢ 2:int
{x : int} ⊢ x + 2 : int {x : int} ⊢ 3 : int
{x : int} ⊢ x + 2 = 3 : bool
*
87
Left-hand side?
Bin
Bin
Bin
Type Judgments
Example: { x : int } ⊢ x + 2 = 3 : bool
{x : int} ⊢ x : int {x : int} ⊢ 2:int
{x : int} ⊢ x + 2 : int {x : int} ⊢ 3 : int
{x : int} ⊢ x + 2 = 3 : bool
*
88
How to finish?
Bin
Bin
Bin
Type Judgments
Example: { x : int } ⊢ x + 2 = 3 : bool
{x : int} ⊢ x : int {x : int} ⊢ 2:int
{x : int} ⊢ x + 2 : int {x : int} ⊢ 3 : int
{x : int} ⊢ x + 2 = 3 : bool
*
89
Complete proof (type derivation)
Bin
Bin
Bin
Var
Const
Const
Type Judgments
90
Questions?
Takeaways
91
Next Class: More Type Checking
92
Next Class
93