Hi Jeffrey,
While that works for the simple example, it seems to fail for slightly more 
complex examples (Now I don''t feel bad about having had trouble with this 
to begin with!)

The attached a program that demonstrates the problem and the (surprisingly 
messy) fix as shown by the following output

location() is (0, 3)
> G1 first is 1
> G1 last is 3
> input span starts at 0
> span length is 7
>
> *Jeffrey's literal is not the entire match: #defineMike's literal is the 
> entire match:  #define foo bar*
>
>
In any case, I have a working solution now, so I'm good to go.

Thanks,

Mike

-- 
You received this message because you are subscribed to the Google Groups 
"marpa parser" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/d/optout.
use Marpa::R2;

my $dsl = <<'END_OF_DSL';
:default ::= action => [name,values]
lexeme default = latm => 1

:start ::= matches

matches ::= match+
match ::= id | macro action => do_macro_match
macro ::= '#define' identifier identifier
id ::= identifier

identifier ~ [\w]+
:discard ~ whitespace
whitespace ~ [\s]+

END_OF_DSL


my $grammar = Marpa::R2::Scanless::G->new( { source => \$dsl } );
my $recce = Marpa::R2::Scanless::R->new(
    { grammar => $grammar, semantics_package => 'CodeProcess' } );

my $input = '#define foo bar';
my $length_read = $recce->read( \$input );

my $value_ref = $recce->value;
my $value = ${$value_ref};


sub CodeProcess::do_macro_match {
    my ($g1_before, $g1_after) = Marpa::R2::Context::location();
    print "location() is ($g1_before, $g1_after)\n";
    # location() returns the g1 location before the token
    # and the g1 location after the last token
    # of a symbol

    my $g1_first = $g1_before + 1;
    my $g1_last = $g1_after;
    # We regard a token as *at* a g1 location if the g1
    # location is after it, so that the first token included
    # in a symbol is the one *after* the start returned
    # by location.  The last token in the symbol is "at",
    # the g1 location *after* it, so no correction is needed.

    print "G1 first is $g1_first\n";
    print "G1 last is $g1_last\n";
   
    my ($span_beg, $span_length) = $recce->g1_location_to_span(
       $g1_first,
       $g1_last);
    print "input span starts at $span_beg\n";
    print "span length is $span_length\n";
    print "Jeffrey's literal does NOT give the entire match: " . $recce->literal($span_beg, $span_length) . "\n";

    
    my @span1 = $recce->g1_location_to_span($g1_before);
    my @span2 = $recce->g1_location_to_span($g1_after);
    print "Mike's literal gives the entire match:  ".$recce->literal($span1[0] +$span1[1], $span2[0] + $span2[1] - $span1[0] - $span1[1])."\n";

 }

Reply via email to