You are on page 1of 101

λλλλλ

data made λ
λλ λλ
λ
λ λ
out of λ
λ
λ λ
λ
λ

functions λ
λ
λ λ λ
λλλλ λ
λ λ
λλ λλ
λλλλλ
#ylj2016
@KenScambler For faster
monads!
Diogenes of Sinope
412 – 323 BC
• Simplest man of all time
• Obnoxious hobo
• Lived in a barrel

Diogenes of Sinope
412 – 323 BC
I’ve been using this bowl
like a sucker!
Um….
what
[a, b, c, d]
"abcd"

IF x THEN y ELSE z

INT
WHILE cond {…}

λa -> b STRUCT {
BOOL fields…
}
Strings are
[a, b, c, d]
pretty much
arrays
IF x THEN y ELSE z

INT
WHILE cond {…}

λa -> b STRUCT {
BOOL fields…
}
Recursion can [a, b, c, d]
do loops
IF x THEN y ELSE z

INT

λa -> b STRUCT {
BOOL fields…
}
Recursive data
structures can do
lists IF x THEN y ELSE z

INT

[a,b,c,d]
λa -> b STRUCT {
BOOL fields…
}
Ints can do bools
IF x THEN y ELSE z

INT

[a,b,c,d]
λa -> b STRUCT {
fields…
}
IF x THEN y ELSE z

INT

[a,b,c,d]
λa -> b STRUCT {
fields…
}
λa -> b

[a,b,c,d]
STRUCT
λa -> b
Lambda calculus
Alonzo Church
1903 - 1995
λa -> b
Lambda calculus
Alonzo Church
1903 - 1995
Church encoding
We can make any
data structure out of
functions!
Booleans

Bool
Church booleans

Bool result
Church booleans
If we define everything you
can do with a structure, isn’t
that the same as defining
Bool result
the structure itself?
TRUE
or
FALSE
“What we do if
it’s true”

TRUE result
or
FALSE
“What we do if
it’s false”

TRUE
or
FALSE result
TRUE result
or result
FALSE result
() result
result
() result
result
result
result
The Church encoding
of a boolean is:

r r r
type CBool = forall r. r -> r -> r

cTrue :: CBool
cTrue x y = x

cFalse :: CBool
cFalse x y = y

cNot :: CBool -> CBool


cNot cb = cb cFalse cTrue

cAnd :: CBool -> CBool -> CBool


cAnd cb1 cb2 = cb1 cb2 cFalse

cOr :: CBool -> CBool -> CBool


cOr cb1 cb2 = cb1 cTrue cb2
Natural numbers
0
1
2
3
4

Natural numbers
0
0 +1
0 +1 +1
0 +1 +1 +1
0 +1 +1 +1 +1

Natural numbers
0 Natural
0 +1 numbers form
0 +1 +1 a data
structure!
0 +1 +1 +1
0 +1 +1 +1 +1

Giuseppe Peano
1858 - 1932
Natural Peano numbers

Nat = Succ(Nat)
or
Zero

Giuseppe Peano
1858 - 1932
Now lets turn it
into functions!
Nat = Succ(Nat)
or
Zero
“If it’s a successor”

Succ(Nat) result
or
Zero
Succ(Nat)
or “If it’s zero”
Zero result
Succ(Nat) result
or result
Zero result
Nat result
result
() result
Nat result
result
result
Nat result
() result
Nat
() result
Nat
()
Nat
()
Nat
result result
result
result
The Church encoding
of natural numbers is:

(r r) r r
type CNat = forall r. (r -> r) -> r -> r

c0, c1, c2, c3, c4 :: CNat

c0 f z = z
c1 f z = f z
c2 f z = f (f z)
c3 f z = f (f (f z))
c4 f z = f (f (f (f z)))

cSucc :: CNat -> CNat


cSucc cn f = f . cn f

cPlus :: CNat -> CNat -> CNat


cPlus cn1 cn2 f = cn1 f . cn2 f

cMult :: CNat -> CNat -> CNat


cMult cn1 cn2 = cn1 . cn2
type CNat = forall r. (r -> r) -> r -> r

c0, c1, c2, c3, c4 :: CNat

c0 f = id
c1 f = f
c2 f = f . f
c3 f = f . f . f
c4 f = f . f . f . f

cSucc :: CNat -> CNat


cSucc cn f = f . cn f

cPlus :: CNat -> CNat -> CNat


cPlus cn1 cn2 f = cn1 f . cn2 f

cMult :: CNat -> CNat -> CNat


cMult cn1 cn2 = cn1 . cn2
Performance
Native ints Peano numbers Church numbers

addition O(n) O(1)

O(n2) O(1)
multiplication

O(n) O(n)
print
Performance
Native ints Peano numbers Church numbers

addition O(n) O(1)

O(n2) O(1)
multiplication

O(n) O(n)
print
Church encoding cheat sheet
A a r

A|B (a r) (b r) r
(A, B) (a b r) r

Singleton r

Recursion r r
Cons lists

List a = Cons(a, List a)


or

Nil
Cons(a, List a) result
or result
Nil result
(a, List a) result
result
() result
(a, result) result
result
result
a result result
result
result
The Church encoding
of lists is:

(a r r) r r
The Church encoding
of lists is:

(a r r) r r

AKA: foldr
Functors
a
Functors
a
f a
Functors
a
f a
f (f a)
They compose!
Functors
a
f a What if we make a
f (f a) “Church numeral” out of
f (f (f a)) them?
Free monads
a
f a
f (f a)
f (f (f a))
f (f (f (f a)))
Free monad >>=

a
Free monad >>=

a
fmap
Free monad >>=

f a
Free monad >>=

f a
fmap
Free monad >>=

f a
fmap
Free monad >>=

f (f a)
Free monad >>=

f (f a)
fmap
Free monad >>=

f (f a)
fmap
Free monad >>=

f (f a)
fmap
Free monad >>=

f (f (f a))
Free monad >>=

f (f (f a))
fmap
Free monad >>=

f (f (f a))
fmap
Free monad >>=

f (f (f a))
fmap
Free monad >>=

f (f (f a))
fmap
λn  [n+1, n*2]
3
λn  [n+1, n*2]
4 6
λn  [n+1, n*2]
4 6 fmap
λn  [n+1, n*2]

5 8 7 12
λn  [n+1, n*2]
fmap

5 8 7 12
λn  [n+1, n*2]

5 8 7 12 fmap
λn  [n+1, n*2]

6 10 9 16 8 14 13 24
λn  Wrap [Pure (n+1), Pure (n*2)]

3
λn  Wrap [Pure (n+1), Pure (n*2)]

3 >>=
λn  Wrap [Pure (n+1), Pure (n*2)]

4 6
λn  Wrap [Pure (n+1), Pure (n*2)]

4 6 >>=
λn  Wrap [Pure (n+1), Pure (n*2)]

4 6 fmap
λn  Wrap [Pure (n+1), Pure (n*2)]

4 6 >>=
λn  Wrap [Pure (n+1), Pure (n*2)]

5 8 7 12
λn  Wrap [Pure (n+1), Pure (n*2)]

>>=

5 8 7 12
λn  Wrap [Pure (n+1), Pure (n*2)]

fmap

5 8 7 12
λn  Wrap [Pure (n+1), Pure (n*2)]

5 8 7 12 >>=
λn  Wrap [Pure (n+1), Pure (n*2)]

5 8 7 12 fmap
λn  Wrap [Pure (n+1), Pure (n*2)]

5 8 7 12 >>=
λn  Wrap [Pure (n+1), Pure (n*2)]

6 10 9 16 8 14 13 24
Free monads

Free a = Wrap f (Free f a)


or

Pure a
Wrap f (Free f a) result
or result
Pure a result
f (Free f a) result
result
a result
f result result
result
a result
The Church encoding
of free monads is:

(f r r) (a r) r
Bind is constant time!

(f r r) (a r) r
>>=
CFree f b
λa -> b
λa -> b

λa -> b

You might also like