Home > Uncategorized > Disecting subsets

Disecting subsets

While fighting with htmlily.p6 I found myself in need of a tool that shows me the structure of a pod6 file. Since all nodes are subclasses of Pod::Block and it’s tree structure is walked through simply by recursively descending into .contents, it was easily done. Just recurse and print .^name with some indentation. Putting a stack on walks back is needed because Pod::Block doesn’t provide a .parent method. A bit ugly but not really a problem.

What did confuse me was the fact that .^name on subsets that provide Pod::FormattingCode with a better name didn’t carry a proper type name. And in fact, a subset does inject a new name into the scope but does not change the type of an object that passed a type check against it.

subset FooStr of Str;
my FooStr $s;
sub f(FooStr $s){ say $s.^name };
f("abc");
# OUTPUT«Str␤»

That is fine if you want to use a subset as a type check. Since it passed the check, it must be of that type or a type that behaves in the same way.

I wanted to do introspection, what means turning a type object into a name. Even worse I wanted to turn a type object into a name of a type that is narrower. Since there is no reference from a type to all its sub types, Perl 6 could not help me there. At least not directly.

Luckily I put the subsets into a inline package. When you stick Foo::Bar:: in front of a name, Perl 6 will kindly generate a package for you and put the new types inside. Since a package is a Stash with a funky name, we can iterate over it’s key-value-Pairs. The keys are names and the values are type objects.

Pod::FormattingCode::.pairs.first({ $node ~~ $^a.value }).key

In my case there is a 1:1 relationship between a subset and it’s base type properties, so I can be sure that the first match is correct.

A nice example how using common data structures in the language implementation and exposing them to the programmer, can help Perl 6 to help you.

Advertisements
Categories: Uncategorized

Leave a Reply

Please log in using one of these methods to post your comment:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: