lgn8412 has asked for the wisdom of the Perl Monks concerning the following question:
Hi! I'm seeking some wisdom on using the Parse::RecDescent module, I'm currently making an interpreter and I want it to be able to read parentheses, here's what I have so far:
#!/usr/bin/perl -w use strict; use Parse::RecDescent; use Data::Dumper; use vars qw(%VARIABLE); # Enable warnings within the Parse::RecDescent module. $::RD_ERRORS = 1; # Make sure the parser dies when it encounters an e +rror $::RD_WARN = 1; # Enable warnings. This will warn on unused rules & +c. $::RD_HINT = 1; # Give out hints to help fix problems. # $::RD_TRACE = 1; # Trace the whole thing my $grammar = <<'_EOGRAMMAR_'; # Terminals (macros that can't expand further) # startrule: instruction(s /;/) eofile instruction : print_instruction | assign_instruction print_instruction : /print/i expression { print $item{expression}."\n" } assign_instruction : VARIABLE "=" expression { $main::VARIABLE{$item{VARIABLE}} = $item{expre +ssion} } expression : '(' expression ')' { return $item[2] } | INTEGER OP expression { return main::expression(@item) } | STRING '+' expression { return main::concat(@item) } | VARIABLE OP expression { return main::expression(@item) } | INTEGER | VARIABLE { return $main::VARIABLE{$item{VARIABLE}} } | STRING OP : m([-+*/%]) # Mathematical operators INTEGER : /[+-]?[0-9]*\.?[0-9]+/ # Signed integers VARIABLE : /\w[a-z0-9_]*/i # Variable STRING : /'.*?'/ eofile : /^\Z/ _EOGRAMMAR_ sub expression { shift; my ($lhs,$op,$rhs) = @_; $lhs = $VARIABLE{$lhs} if $lhs=~/[^-+(\.)0-9]/; return eval "$lhs $op $rhs"; } sub concat { shift; my ($lhs,$op,$rhs) = @_; $lhs =~ s/^'(.*)'$/$1/; $rhs =~ s/^'(.*)'$/$1/; return "$lhs$rhs" } my $parser = Parse::RecDescent->new($grammar); #print "a=2\n"; $parser->startrule("a= 'hola ' + 3.2 ") +; #print "b=1+2.2\n"; $parser->startrule("b=1+2.2"); #print "print a\n"; $parser->startrule("print a"); #print "print b\n"; $parser->startrule("print b"); print "print 2+2/4\n"; $parser->startrule("print 2+2/4"); #print "print 2+-2/4\n"; $parser->startrule("print 2+-2/4"); #print "a = 5 ; print a\n"; $parser->startrule("a = 5 ; print a");
As you can see, I used an example on the recdescent module (which I found here http://bit.ly/Sjgdhf) and basically added strings and some other functions, as I have it now I really don't know if I have to change drastically the grammar in order to be able to read parentheses and nested parentheses.. I'd really appreciate some help on this, I've been busting my head with the trace option but have not been successful so far, any ideas??
|
|---|
| Replies are listed 'Best First'. | |
|---|---|
|
Re: Help on Parse::RecDescent!
by tobyink (Canon) on Oct 28, 2012 at 16:32 UTC | |
by tobyink (Canon) on Oct 28, 2012 at 18:12 UTC | |
by lgn8412 (Initiate) on Nov 05, 2012 at 17:03 UTC |