Ethiopian multiplication in Perl6

1,546 views
1,350 views

Published on

Perl6 introduces a variety of tools for functional programming and writing readable code. Among them parameter declarations and lazy lists. This talk looks at how to get Perl6, where to find examples on RakudoCode, and how to use Perl6 functional tools for converting an algorithm from imperative to functional code, including parallel dispatch with the ">>" operator.

Published in: Technology, Education
0 Comments
1 Like
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total views
1,546
On SlideShare
0
From Embeds
0
Number of Embeds
7
Actions
Shares
0
Downloads
6
Comments
0
Likes
1
Embeds 0
No embeds

No notes for slide

Ethiopian multiplication in Perl6

  1. 1. Hyper-Multiplying Ethiopians: Lambdas, Lazyness, & Perl6 Steven Lembark Workhorse Computing lembark@wrkhors.com Hyper-Multiplying Ethiopians: Lambdas, Lazyness, & Perl6
  2. 2. Welcome to Perl6 Rakudo­Star distro. Rosetta Code. Ethiopic Multiplication: What it is. More than one way to do it.
  3. 3. Rakudo Star: Perl6 in a tarball Pretty much what you are used to: Snag a tarball or pull from GitHub. perl Configure; make all test install;
  4. 4. Acquiring Rakudo-Star Call it “Rakudo” from now on. http://rakudo.org/
  5. 5. Acquiring Rakudo-Star Quareterly updates are in ./downloads/star wget .../rakudo-star-2016.01.tar.gz; gzip -dc < *.tar.gz | tar xf -; cd rakudo-star-2016.01; less README;
  6. 6. Acquiring Rakudo-Star Quarterly updates are in ./downloads/star wget .../rakudo-star-2013.10.tar.gz; gzip -dc < *.tar.gz | tar xf -; cd rakudo-star-2013.10; perl Configure.pl –prefix=/opt/perl6 --backends=moar --gen-nqp --gen-moar && make all test install;
  7. 7. Information on Perl6 rakudo.org has links to everything else Perl6­ish. Rakudo's own doc's page is at: <http://rakudo.org/documentation> Also the Perl Maven: Gabor Szabo <http://perl6maven.com/> For example: ./parsing-command-line-arguments-perl6
  8. 8. Rosetta Code Wonderful site, if you care about languages. Various algorithms, variety of languages.  Perl6 versions largely coded by Larry Wall.
  9. 9. Ethiopian Multiplication .../wiki/Ethiopian_Multiplication Developed in the time of roman numerals: MCMXIV * XXXIIV = ?? Using integer math: Halve the first number to 1, double the second.  Sum doubled numbers for odd halved ones.
  10. 10. Maybe an example will help... 17 x 34 write down two numbers...
  11. 11. Maybe an example will help... 17 x 34 8 halve the first number to 1 4 using integer math... 2 1
  12. 12. Maybe an example will help... 17 x 34 8 68 4 136 double the second number... 2 272 1 544
  13. 13. Maybe an example will help... 17 34 8 68 4 136 2 272 1 544 sum the doubles with odd halves...
  14. 14. Maybe an example will help... 17 34 8 68 4 136 2 272 1 544 578 Viola!, the product
  15. 15. Plan 1: Imperative programming Loop over the halved value. Doubling the other. Summing as you go.
  16. 16. What it looks like in Perl5 sub halve { int((shift) / 2) } sub double { (shift) * 2 } sub iseven { ((shift) & 1) == 0 } sub ethiopicmult { my ($plier, $plicand) = @_; my $r = 0; while ($plier >= 1) { $r += $plicand unless iseven $plier; $plier = halve $plier; $plicand = double $plicand; } return $r; }
  17. 17. Perl6 More ways to do it: Parameter types. Local functions.
  18. 18. Stand-alone subs sub halve (Int $n is rw) { $n div= 2 } # integer divide sub double (Int $n is rw) { $n *= 2 } sub even (Int $n --> Bool) { $n %% 2 } # return, is-divisible sub ethiopicmult ( Int $a is copy, Int $b is copy --> Int ) { my $r = 0; while $a { even $a or $r += $b; halve $a; double $b; } return $r; }
  19. 19. Embedded subs sub ethiopicmult ( Int $a is copy, Int $b is copy --> Int ) { sub halve (Int $n is rw) { $n div= 2 }; # subs are sub double (Int $n is rw) { $n *= 2 }; # lexically sub even (Int $n --> Bool) { $n %% 2 }; # scoped my $r = 0; while $a { even $a or $r += $b; halve $a; double $b; } return $r; }
  20. 20. Self-contained with lexical subs sub ethiopicmult ( Int $a is copy, Int $b is copy --> Int ) { my &halve = * div= 2; # placeholders save my &double = * *= 2; # syntax. my &even = * %% 2; my $r = 0; loop # a.k.a. for(;;) { even $a or $r += $b; halve $a or return $r; double $b; } }
  21. 21. Self-contained with lexical subs sub ethiopicmult ( Int $a is copy, Int $b is copy --> Int ) { state &halve = * div= 2; # “state” avoids state &double = * *= 2; # re-compiling. state &even = * %% 2; my $r = 0; loop { even $a or $r += $b; halve $a or return $r; double $b; } }
  22. 22. Even more than... Functional Programming: Yet Another Way to Avoid Spaghetti Code. Neither “structured programming” nor “objects”. Manage state and side effects.
  23. 23. The Evil State State is hard to maintain. Coding errors: losing, failed, multiple updates... Avoiding it reduces errors.
  24. 24. Unintended Consequences sub loop { double $b; even $a or $r += $b; halve $a or return $r; double $b; }
  25. 25. “Functional” programming e.g., Haskell, Scheme, Scala, Clojure, Perl6 Declarative: describe the answer not steps. (e.g., order of execution in Haskell is derived).
  26. 26. Ideal: pure functional code Fully deterministic function calls. Avoid state & side­effects. No surprises. Easy to test, with full validation.
  27. 27. Catch: it doesn't work Examples? time() random() readline() fetchrow_array() Result: Be realistic.
  28. 28. Looking at it in Perl6 Replace steps with declarations. Say “how” not “what”.
  29. 29. Declarative definition sum a list ...
  30. 30. Declarative definition sum a list ... selecting the doubled values whose halved  entry is odd ...
  31. 31. Declarative definition sum a list ... selecting the doubled values whose halved  entry is odd ... from a list of pairs ...
  32. 32. Declarative definition sum a list ... selecting the doubled values whose halved  entry is odd ... from a list of pairs ... halving the first value to one, doubling the second one each time.
  33. 33. Iterators & maps & zips, oh my! sub ethiopicmult ( Int $a is copy, Int $b is copy --> Int ) { state &halve = * div= 2; state &double = * *= 2; state &odd = * % 2; [+] # list operator [] iterates '+'. map # map pulls two values each time. { $^col_2 if odd $^col_1 # parameters extract in lexical order. }, zip # new list from the list arguments ( $a, &halve ... 1 ; # semi-colon separates lists $b, &double ... * # indefinite lazy list ); }
  34. 34. Iterators & maps & zips, oh my! sub ethiopicmult ( Int $a is copy, Int $b is copy --> Int ) { state &halve = * div= 2; state &double = * *= 2; [+] map -> $half, $dbl # named parameters { $dbl if $half % 2 }, zip ( $a, &halve ... 1 ; $b, &double ... * ); }
  35. 35. Inline list generators replace subs sub ethiopicmult ( Int $a is copy, Int $b is copy --> Int ) { # what you see is all you get [+] map -> $half, $dbl { $dbl if $half % 2 }, zip ( $a, * div 2 ... 1 ; # implicit subs $b, * * 2 ... * ) }
  36. 36. Ternary Operator Makes 0 Explicit sub ethiopicmult { my ($a,$b) = @_; # still works [+] map -> $half, $dbl { $half % 2 ?? $dbl # wider ?? !! easier to see !! 0 # or () }, zip ( $a, &halve ... 1; $b, &double ... * ) }
  37. 37. Result Minimal, declarative syntax. Avoid order­of­execution errors. Hopefully more descriptive, easier to maintain.
  38. 38. Result Minimal, declarative syntax. Avoid order­of­execution errors. Hopefully more descriptive, easier to maintain. But wait! There's More!
  39. 39. What you are used to Processing a list with map: @result = map { $_->$method( @argz ) } @inputs; Single­threaded. Fixed order of input. Fixed order of processing.
  40. 40. Perl6 adds “hyperoperators” The “»” or “>>” parallel execution: @result = @objects».&function( @args ); @objects  blessed or class, literal or variable. @result   in the same order as @objects. Order of execution is indeterminate.
  41. 41. Zipping pairs, not flat lists. “zip” generates a flat list. “Z=>” normally used for hashes: my %hash = ( ( $a, * div 2 … 1 ) Z=> ( $b, * * 2 … * ) ); List of key:value pairs: ( ( 17, 34 ) ; ( ( 8, 68 ) ; … )
  42. 42. Processing pairs Pair object has “key” and “value”: sub odd_values( $pair ) { $pair.key % 2 ?? $pair.value !! () }
  43. 43. Generating the list of odd values [+] ( ( $a, * div 2 … 1 ) Z=> ( $b, * * 2 … * ) ) ».odd_values Selection of odd values is parallel. Generation and sum are single­threaded.
  44. 44. Hyper-whybotherators? “$a % 2” ?? Comparing DNA or proteins... … complex financial simulation... … playing conway's game of life? without loops, forks, breaks, joins,  co routines, or queues?‑
  45. 45. What's this got to do with FP? Hyperoperators lack repeatable sequence. Side effects, state? Fix: FP [­ish] functions for hyperoperators.
  46. 46. Reading on the ceiling Catch: map­ish code reads “upside down”. Wish you could read it going down the page?
  47. 47. Feeding on the floor Feed operator: ( ( $a, * div 2 … 1 ) Z=> ( $b, * * 2 … * ) )  ».odd_values ==> [+] odd_values into [+] block­iterator.
  48. 48. The result sub ethiopic_hyper_mult( $a, $b ) { sub odd_values( $pair ) { $pair.key % 2 ?? $pair.value !! () } (( $a, * div 2 … 1 ) Z=> ( $b, * * 2 … * ) )) >>.&odd_values ==> [+] }
  49. 49. New things in Perl6 %% is “Divisible By" & "div" integer division. my &subname = ... for lexically defined subs. * for parameters. $^foo for block parameters. Parameterized lists with $start, OP, $end. List operators with [ OP ]. Hyperopertors & friends.
  50. 50. Shameless Plug Glacier Hashes are nice for FP. Perl5 is nice for Glacier Hashes. YAPC::NA 2016: FP code & benchmarks. With tail recursion. In Perl5. 
  51. 51. References Monads in Perl5: http://web.archive.org/web/20080515195640/http://sle epingsquirrel.org/monads/monads.html Introduces the basic ideas of functional  programming with monads using Perl5 examples.
  52. 52. References Readable descriptions of “Monad”: https://stackoverflow.com/questions/44965/what-is-a- monad https://stackoverflow.com/questions/2704652/monad- in-plain-english-for-the-oop-programmer-with-no-fp- background
  53. 53. References What databases mean to Functional Programming: <https://stackoverflow.com/questions/8406261/most ­common­pattern­for­using­a­database­in­a­ functional­language­given­desire> The most common pattern for dealing with side­ effects and impurity in functional languages is:     ­ be pragmatic, not a purist ...
  54. 54. References Realistic view of FP: https://stackoverflow.com/questions/330371/are- databases-and-functional-programming-at-odds Functional languages do not have the goal to  remain stateless, they have the goal to make  management of state explicit.
  55. 55. References Good overview of the vocabulary: http://en.wikipedia.org/wiki/Functional_Programming
  56. 56. References Academic description of Monads: http://web.archive.org/web/20071128090030/http://hom epages.inf.ed.ac.uk/wadler/papers/marktoberdorf/baas tad.pdf

×