Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

perl6 Grammar action class method seems not inherited, named capture seems not made

I am trying to parse a csv file to do simple things: extract last name, ID, and birthday, and change format of birthday from m/d/yyyy to yyyymmdd.

(1) I used named capture for birthdays, but it seems that named captures method are not called to make what I want.

(2) Inheriting grammar action methods seems not working for named captures.

What did I do wrong?

my $x = "1,,100,S113*L0,35439*01,John,JOE,,,03-10-1984,47 ELL ST #6,SAN FRANCISCO,CA,94112,415-000-0000,,5720,Foo Bar,06-01-2016,06-01-2016,Blue Cross,L,0,0";

# comma separated lines
grammar insurCommon {
    regex aField  { <-[,]>*? }
    regex theRest { .* }
}    

grammar insurFile is insurCommon {
    regex TOP { <aField> \,\,  # item number
        <aField> \,            # line of business
        <aField> \,            # group number
        <ptID=aField> \,       # insurance ID, 
        <ptLastName=aField> \, # last name, 
        <aField> \,\,\,        # first name
        <ptDOB=aField> \,      # birthday
        <theRest> }
}

# change birthday format from 1/2/3456 to 34560102
sub frontPad($withWhat, $supposedStrLength, $strToPad) {
    my $theStrLength = $strToPad.chars;
    if $theStrLength >= $supposedStrLength { $strToPad; }
    else { $withWhat x ($supposedStrLength - $theStrLength) ~ $strToPad; }
}

class dateAct {
    method reformatDOB($aDOB) {
      $aDOB.Str.split(/\D/).map(frontPad("0", 2, $_)).rotate(-1).join;
    }
}

class insurFileAct is dateAct {
    method TOP($anInsurLine) {
      my $insurID = $anInsurLine<ptID>.Str;
      my $lastName = $anInsurLine<ptLastName>.Str;
      my $theDOB = $anInsurLine<ptDOB>.made; # this is not made;
      $anInsurLine.make("not yet made"); # not yet getting $theDOB to work
    }
    method ptDOB($DOB) { # ?ptDOB method is not called by named capture?
      my $newDOB = reformatDOB($DOB); # why is method not inherited
      $DOB.make($newDOB);
    }
}

my $insurAct = insurFileAct.new;
my $m = insurFile.parse($x, actions => $insurAct);

say $m.made;

And the output is:

===SORRY!=== Error while compiling /home/test.pl
Undeclared routine:
    reformatDOB used at line 41
like image 297
lisprogtor Avatar asked Feb 06 '17 07:02

lisprogtor


3 Answers

You're trying to invoke the non-existing subroutine reformatDOB, not a method.

In contrast to, say, Java, Perl6 does not allow you to omit the invocant, ie the method call has to be written as

self.reformatDOB($DOB)

In addition, there are also shorthand forms like

$.reformatDOB($DOB) # same as $(self.reformatDOB($DOB))
@.reformatDOB($DOB) # same as @(self.reformatDOB($DOB))
...

that additionally impose context on the return value.

like image 159
Christoph Avatar answered Oct 11 '22 02:10

Christoph


Also: why reinvent the wheel? There's Text::CSV for Perl 6:

https://github.com/Tux/CSV

install with either:

panda install Text::CSV

or:

zef install Text::CSV
like image 33
Elizabeth Mattijsen Avatar answered Oct 11 '22 01:10

Elizabeth Mattijsen


You are right in that the action method for the name of the named capture doesn't get called. Instead, it will call the method based on the name of the thing that was matched. I.e. aField will be called.

You can just call self.ptDOB($anInsurLine<ptDOB>) manually from your TOP action method.

like image 1
timotimo Avatar answered Oct 11 '22 00:10

timotimo