82
Functional Pe(a)rls osfameron @ IPW2011, Turin osfameron @ IPW2011, Turin the “purely functional data structures” the “purely functional data structures” edition edition http://www.fickr.com/photos/jef_saf/3493852795/

Functional Pe(a)rls - the Purely Functional Datastructures edition

Embed Size (px)

DESCRIPTION

All new material, this time about one of the fundamental functional datastructures, the Linked List, and the overview of an implementation in Moosey Perl.This covers some of the same material as https://github.com/osfameron/pure-fp-book but perhaps with more explanation (and covering much less material - it was only a 20 minute talk)

Citation preview

Page 1: Functional Pe(a)rls - the Purely Functional Datastructures edition

Functional Pe(a)rls

osfameron @ IPW2011, Turinosfameron @ IPW2011, Turinthe “purely functional data structures” the “purely functional data structures”

editionedition

http://www.fickr.com/photos/jef_saf/3493852795/

Page 2: Functional Pe(a)rls - the Purely Functional Datastructures edition

previously on Functional Pe(a)rls...

(IPW, LPW, YAPC::EU, nwe.pm)currying

operator references: op(+)Acme::MonadsDevel::Declare

Page 3: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

C I A O

vs.

Page 4: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

C I A O

Page 5: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

0th element

C I A O

Page 6: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

0th element

M I A OM I A OM I A O

Page 7: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

0th element

M I A OM I A OM I A O

no kittens were harmed during the making of

this presentation

Page 8: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

2nd element

M I A O

Page 9: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

4th element

M I A O

Page 10: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

max: 3

M I A O

Page 11: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

max: 3

M I A O

Page 12: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

max: 4

M I A O W

4th element

4

Page 13: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

max: 3

M I A O …

100,000

Page 14: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

max: 3

M I A O

Page 15: Functional Pe(a)rls - the Purely Functional Datastructures edition

0 1 2 3

max: 4

M I A O W4

0 1 2 3

max: 5

M I A O W !4 5

Page 16: Functional Pe(a)rls - the Purely Functional Datastructures edition

40 1 2 3

max: 4

M I A O W

0 1 2 3

max: 5

M I A O W !4 5

Page 17: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

C I A O

vs.

Arrays

Page 18: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

C I A O

vs.

Perl @arrays“dynamic array”

Page 19: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

Page 20: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

Page 21: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

Head

Page 22: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

Tail

Page 23: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

Page 24: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

Page 25: Functional Pe(a)rls - the Purely Functional Datastructures edition

I A O

Page 26: Functional Pe(a)rls - the Purely Functional Datastructures edition

A O

Page 27: Functional Pe(a)rls - the Purely Functional Datastructures edition

O

Page 28: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

0th

Page 29: Functional Pe(a)rls - the Purely Functional Datastructures edition

C A O

nth - 1

I

Page 30: Functional Pe(a)rls - the Purely Functional Datastructures edition

C A O

nth[2]?

I

nth[1]?

Page 31: Functional Pe(a)rls - the Purely Functional Datastructures edition

C A OI

nth[0]!nth[2]?

Page 32: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O ?

Page 33: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O ?● tail “ciao” → “iao”

Page 34: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O ?● tail “ciao” → “iao”● tail “iao” → “ao”● tail “ao” → “o”● tail “o” → ?

Page 35: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O ?● tail “ciao” → “iao”● tail “iao” → “ao”● tail “ao” → “o”● tail “o” → “” (the empty string)

Page 36: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

Page 37: Functional Pe(a)rls - the Purely Functional Datastructures edition

Head

List =

Tail(another List)

or...

Page 38: Functional Pe(a)rls - the Purely Functional Datastructures edition

Here comes the science^wPerl!

Page 39: Functional Pe(a)rls - the Purely Functional Datastructures edition

use MooseX::Declare;

BEGIN { role_type 'List' }

role List { requires 'head'; requires 'tail';}

Moose(X::Declare)

Page 40: Functional Pe(a)rls - the Purely Functional Datastructures edition

List::Link

class List::Link with List { has head => (

is => 'ro', isa => 'Any'

); has tail => (

is => 'ro', isa => 'List'

), }

Page 41: Functional Pe(a)rls - the Purely Functional Datastructures edition

List::Link

class List::Link with List { has head => (

is => 'ro', isa => 'Any'

); has tail => (

is => 'ro', isa => 'List'

), }

Page 42: Functional Pe(a)rls - the Purely Functional Datastructures edition

List::Link

class List::Link with List { has head => (

is => 'ro', isa => 'Any'

); has tail => (

is => 'ro', isa => 'List'

), }

Page 43: Functional Pe(a)rls - the Purely Functional Datastructures edition

List::Empty

class List::Empty with List { method head {

die "Can't take head of empty list!" } method tail { die "Can't take tail of empty list!" } }

Page 44: Functional Pe(a)rls - the Purely Functional Datastructures edition

So we can write:

my $list = List::Link->new( head => 'c', tail => List::Link->new( head => 'i', tail => List::Link->new(...

Page 45: Functional Pe(a)rls - the Purely Functional Datastructures edition

Sugar!

my $list = List->fromArray(qw/ c i a o /);

Page 46: Functional Pe(a)rls - the Purely Functional Datastructures edition

Multimethods

use MooseX::MultiMethods;

multi method fromArray ($class:) { return List::Empty->new; }

Page 47: Functional Pe(a)rls - the Purely Functional Datastructures edition

Multimethods

use MooseX::MultiMethods;

multi method fromArray ($class:) { return List::Empty->new; }

Page 48: Functional Pe(a)rls - the Purely Functional Datastructures edition

Multimethods multi method fromArray ($class: $head, @tail) { return List::Link->new( head => $head, tail => $class->fromArray(@tail), ); }

Page 49: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

my $list = List::fromArray(1..1000000);

Page 50: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

my $list = List::fromArray(1..1000000);

Deep recursion on subroutine "List::fromArray" at foo.pl line 20

Page 51: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion! multi method fromArray ($class: $head, @tail) { return List::Link->new( head => $head, tail => $class->fromArray(@tail), ); }

Page 52: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray

Page 53: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray

List::Link->new(..., fromArray)

Page 54: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray

List::Link->new(..., fromArray)

List::Link->new(..., fromArray)

Page 55: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray

List::Link->new(..., fromArray)

List::Link->new(..., fromArray)

List::Link->new(..., fromArray)

Page 56: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray

List::Link->new(..., fromArray)

List::Link->new(..., fromArray)

List::Link->new(..., fromArray)

List::Link->new(..., fromArray)

Page 57: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray

List::Link->new(..., fromArray)

List::Link->new(..., fromArray)

List::Link->new(..., fromArray)

List::Link->new(..., fromArray) $list=

Page 58: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray

List::Link->new(..., fromArray)

List::Link->new(..., fromArray)

List::Link->new(..., fromArray) $list=

Page 59: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray

List::Link->new(..., fromArray)

List::Link->new(..., fromArray) $list=

Page 60: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray

List::Link->new(..., fromArray) $list=

Page 61: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

fromArray $list=

Page 62: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

no warnings 'recursion';$DB::deep = 100_000_000;

Page 63: Functional Pe(a)rls - the Purely Functional Datastructures edition

Eeek! Recursion!

no warnings 'recursion';$DB::deep = 100_000_000;

Papering over the cracks

Page 64: Functional Pe(a)rls - the Purely Functional Datastructures edition

Tail Call Elimination

Sub::Call::TailSub::Call::Recur

by nothingmuch

Page 65: Functional Pe(a)rls - the Purely Functional Datastructures edition

Tail call elimination

fromArray

Page 66: Functional Pe(a)rls - the Purely Functional Datastructures edition

Tail call elimination

List::Link->new(..., fromArray)

Page 67: Functional Pe(a)rls - the Purely Functional Datastructures edition

Tail call elimination

List::Link->new(..., fromArray)

Page 68: Functional Pe(a)rls - the Purely Functional Datastructures edition

Tail call elimination

List::Link->new(..., fromArray)

Page 69: Functional Pe(a)rls - the Purely Functional Datastructures edition

Tail call elimination

List::Link->new(..., fromArray)

Page 70: Functional Pe(a)rls - the Purely Functional Datastructures edition

Tail call elimination

List::Link->new(..., fromArray) $list=

Page 71: Functional Pe(a)rls - the Purely Functional Datastructures edition

Tail Call Elimination

use Sub::Import 'Sub::Call::Tail' tail => { -as => 'tail_call' };

multi method fromArray ($self: $head, @tail) { tail_call List::Link->new( head => $head, tail => $self->fromArray(@tail), );}

Page 72: Functional Pe(a)rls - the Purely Functional Datastructures edition

Indexing into List

multi method nth (List::Empty $self: Int $pos)

{ die "Can't index into an Empty list"; }

Page 73: Functional Pe(a)rls - the Purely Functional Datastructures edition

Indexing into List

multi method nth (Int $pos where { $_ == 0 })

{ return $self->head; }

Page 74: Functional Pe(a)rls - the Purely Functional Datastructures edition

Indexing into List

multi method nth (Int $pos where { $_ > 0 })

{ tail_call $self->tail->nth( $pos - 1 ); }

Page 75: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

M

Page 76: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

M W

Page 77: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

M WMutation leads to bugs (and misspellings!)

Page 78: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

M WI A O

Page 79: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

C I B

Page 80: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

C I B

Copy everything upstream of a changeDownstream of changes can be shared

Page 81: Functional Pe(a)rls - the Purely Functional Datastructures edition

C I A O

C I B

Doubly linked lists have no downstream!

O

Page 82: Functional Pe(a)rls - the Purely Functional Datastructures edition

pure-fp-book

● https://github.com/osfameron/pure-fp-book● Purely Functional Data Structures for the...

● Impure● Perl Programmer● Working Programmer● Mutable, Rank-Scented Many