开发者

cannot parse using Parse::Lex

开发者 https://www.devze.com 2023-04-04 14:06 出处:网络
I am using Perl version 5.12.4 from active state on Windows XP(Version 5.1.2600).Installed ParseLex 2.20.

I am using Perl version 5.12.4 from active state on Windows XP(Version 5.1.2600).Installed ParseLex 2.20. Trying to run this code from Pro Perl Parsing book from Apress.

#!/usr/bin/perl

use Parse::Lex;

#defines the tokens
@token=qw(  
BegParen [\(]
EndParen [\)]
Operator [-+*/^]
Number   [-?\d+|-?\d+\.\d*]
);
$lexer=Parse::Lex->new(@token); #Specifies the lexer
$lexer->from(STDIN); #Specifies the input source

TOKEN:
while(1){ #1 will be returned unless EOI
$token=$lexer->next;
if(not $lexer->eoi){
    print $token->name . " " . $token->text . " " . "\n";
}
else {last TOKEN;}
}

As this was not working I simplified by Number [-?\d+]. It is telling me "Can't call method "name" on an undefined value ".It is not recognizing $token->name & $token->text. What I am missing here? Please help.

As per Alexandar's suggestion I have changed the code to $lexer->from(*STDIN); and able to successfully read fro开发者_JS百科m stdin.Also changed Number [(-?\d+)|(-?\d+.\d*)].Now when I feed 43.4*15^2 to the STDIN the output I get is:

Number 4
Number 3
Number .
Number 4
Operator *
Number 1
Number 5
Operator ^
Number 2
Can't call method "name" on an undefined value at listing1-1.pl line 20, <STDIN>.

Here line 20 is print $token->name, " ", $token->text,"\n".


It should be "Number -?\d+|-?\d+.\d*" and to read from STDIN "from" method should be called this way:

$lexer->from(\*STDIN);

Update full code with better error handling and fixes:

#!/usr/bin/perl

use Parse::Lex;

#defines the tokens
my @token=(qw(  
BegParen [\(]
EndParen [\)]
Operator [-+*/^]
Number   -?\d+(?:\.\d*)?
NEWLINE  \n
     ),
     qw(ERROR  (?s:.*)), sub {
       print STDERR "ERROR: buffer content->", $_[0]->lexer->buffer, "<-\n";
       die qq!can\'t analyze: "$_[1]"!;
     }
);
my $lexer=Parse::Lex->new(@token); #Specifies the lexer
$lexer->from(\*STDIN); #Specifies the input source

TOKEN:
while(1){ #1 will be returned unless EOI
  my $token=$lexer->next;
  if (not $lexer->eoi){
    print $token->name . " " . $token->text . " " . "\n";
  }
  else {last TOKEN;}
}

Also see Parse::Lex documentation.

0

精彩评论

暂无评论...
验证码 换一张
取 消