Search code examples
regexactionrakuproto

perl6 grammar to do substitution


Ok, I am learning perl6 and I am trying to do something really simple: use grammar to change matched text according to the action object. But I failed and I don't know why. Please excuse me for such simple questions. I am not in the tech or programming industry. So, please be patient with me, okay?

I want to change "jan" to 01 and "feb" to 02; so simple:

grammar month {
    regex TOP { (\s* <mon> \s*)+ }
    proto regex mon {*}
    regex mon:sym<jan> { <sym> }
    regex mon:sym<feb> { <sym> }
}
class monAct {
    method TOP ($/) {
    make $<mon>.made;
    }
    method mon:sym<jan> ($/) { make "01"; };
    method mon:sym<feb> ($/) { make "02"; };
}
my $m = month.parse("jan feb jan feb", actions => monAct.new);
say $m.made; # it says Nil instead of "01 02 01 02" that I want; 

So, what did I do wrong here? Thanks.


Solution

  • <mon> is scoped to the capturing group, not the TOP rule. You could index into the match object to get at it, but it's probably easier to use a non-capturing group instead:

    regex TOP { [\s* <mon> \s*]+ }
    

    Additionally, due to the + quantifier, you will not get a single match object, but a list. You can use >> or map to get at the payload, eg

    method TOP ($/) { make $<mon>>>.made }