Last active
December 15, 2015 05:59
-
-
Save masak/5213423 to your computer and use it in GitHub Desktop.
Yes, Perl 6 can do ADTs. Sort of.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# data Tree a = Branch (Tree a) (Tree a) | Leaf a | |
subset Tree of Hash where &is_branch | &is_leaf; | |
sub is_branch($_) { | |
.keys == 2 | |
&& .exists('left') | |
&& .<left> ~~ Tree | |
&& .exists('right') | |
&& .<right> ~~ Tree | |
} | |
sub is_leaf($_) { | |
.keys == 1 | |
&& .exists('cargo') | |
} | |
# We can construct nice subtypes from the subroutines, | |
# too. | |
subset Branch of Tree where &is_branch; | |
subset Leaf of Tree where &is_leaf; | |
# Just by using subtypes, we have basically co-opted | |
# smartmatching, which is a big part of the battle won. | |
my $tree = { | |
left => { cargo => 1 }, | |
right => { | |
left => { cargo => 2 }, | |
right => { cargo => 3 }, | |
}, | |
}; | |
say $tree ~~ Tree; # True | |
say { | |
left => "lol, not a Tree" | |
} ~~ Tree; # False | |
say "also not a Tree" ~~ Tree; # False | |
# 'when' statements are basically sugar for smartmatching, | |
# and so they work, too. This allows us to | |
sub sum_leaves(Tree $_) { | |
when Branch { sum_leaves(.<left>) + sum_leaves(.<right>) } | |
when Leaf { .<cargo> } | |
} | |
say sum_leaves($tree); # 6 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment