in reply to Break string into array
Update: Actually, it's a bit more different than I thought because you said you can't have both OR and AND in the same list.
# make_parser.pl use strict; use warnings; use Parse::RecDescent qw( ); my $grammar = <<'__EOI__'; { use strict; use warnings; sub dequote { my ($s) = @_; $s =~ s/^"//; $s =~ s/"\z//; $s =~ s/\\(.)/$1/sg; return $s; } } parse : list /\Z/ { $item[1] } list : term list_[ $item[1] ] list_ : "AND" <commit> and_list { [ $item[1] => $arg[0], @{$item[3]} ] } | "OR" <commit> or_list { [ $item[1] => $arg[0], @{$item[3]} ] } | { $arg[0] } and_list : term and_list_ { [ $item[1], @{$item[2]} ] } and_list_ : "AND" <commit> term and_list_ { [ $item[3], @{$item[4]} ] } | { [] } or_list : term or_list_ { [ $item[1], @{$item[2]} ] } or_list_ : "OR" <commit> term or_list_ { [ $item[3], @{$item[4]} ] } | { [] } term : IDENT | STRING | '(' list ')' { $item[2] } IDENT : /\w+/ STRING : /"(?:\\.|[^\\])*"/s { dequote($item[1]) } __EOI__ Parse::RecDescent->Precompile($grammar, 'Parser') or die("Bad grammar\n");
# test.pl use strict; use warnings; use Data::Dumper qw( Dumper ); use Parser qw( ); my $text = 'dogs OR cats OR "flying fish" OR (shrimp AND squid)'; my $parser = Parser->new(); print(Dumper($parser->parse($text)));
>perl make_parser.pl >perl test.pl $VAR1 = [ 'OR', 'dogs', 'cats', 'flying fish', [ 'AND', 'shrimp', 'squid' ] ];
Update: Small changes to grammar to eliminate backtracking.
|
|---|
| Replies are listed 'Best First'. | |
|---|---|
|
Re^2: Break string into array
by Anonymous Monk on Sep 18, 2009 at 08:48 UTC | |
by ikegami (Patriarch) on Sep 18, 2009 at 14:59 UTC | |
by Anonymous Monk on Sep 18, 2009 at 15:23 UTC | |
by ikegami (Patriarch) on Sep 18, 2009 at 16:22 UTC |