Add => action rule for an entire sequence

db4
Chris Double 2008-03-30 17:17:31 +13:00
parent 691d26068d
commit af9e27823a
2 changed files with 35 additions and 5 deletions

View File

@ -144,6 +144,23 @@ IN: peg.ebnf.tests
"Z" [EBNF foo=[^A-Z] EBNF] call "Z" [EBNF foo=[^A-Z] EBNF] call
] unit-test ] unit-test
{ V{ "1" "+" "foo" } } [
"1+1" [EBNF foo='1' '+' '1' [[ drop "foo" ]] EBNF] call parse-result-ast
] unit-test
{ "foo" } [
"1+1" [EBNF foo='1' '+' '1' => [[ drop "foo" ]] EBNF] call parse-result-ast
] unit-test
{ "foo" } [
"1+1" [EBNF foo='1' '+' '1' => [[ drop "foo" ]] | '1' '-' '1' => [[ drop "bar" ]] EBNF] call parse-result-ast
] unit-test
{ "bar" } [
"1-1" [EBNF foo='1' '+' '1' => [[ drop "foo" ]] | '1' '-' '1' => [[ drop "bar" ]] EBNF] call parse-result-ast
] unit-test
{ V{ V{ 49 } "+" V{ 49 } } } [ { V{ V{ 49 } "+" V{ 49 } } } [
#! Test direct left recursion. #! Test direct left recursion.
#! Using packrat, so first part of expr fails, causing 2nd choice to be used #! Using packrat, so first part of expr fails, causing 2nd choice to be used

View File

@ -111,7 +111,10 @@ C: <ebnf> ebnf
'range-parser' , 'range-parser' ,
'any-character' , 'any-character' ,
] choice* , ] choice* ,
[
"=" syntax ensure-not , "=" syntax ensure-not ,
"=>" syntax ensure ,
] choice* ,
] seq* [ first ] action ; ] seq* [ first ] action ;
DEFER: 'choice' DEFER: 'choice'
@ -178,21 +181,30 @@ DEFER: 'choice'
'optional' sp , 'optional' sp ,
] choice* ; ] choice* ;
: 'action' ( -- parser )
"[[" 'factor-code' "]]" syntax-pack ;
: 'sequence' ( -- parser ) : 'sequence' ( -- parser )
#! A sequence of terminals and non-terminals, including #! A sequence of terminals and non-terminals, including
#! groupings of those. #! groupings of those.
[ [
[ [
('sequence') , ('sequence') ,
"[[" 'factor-code' "]]" syntax-pack , 'action' ,
] seq* [ first2 <ebnf-action> ] action , ] seq* [ first2 <ebnf-action> ] action ,
('sequence') , ('sequence') ,
] choice* repeat1 [ ] choice* repeat1 [
dup length 1 = [ first ] [ <ebnf-sequence> ] if dup length 1 = [ first ] [ <ebnf-sequence> ] if
] action ; ] action ;
: 'actioned-sequence' ( -- parser )
[
[ 'sequence' , "=>" syntax , 'action' , ] seq* [ first2 <ebnf-action> ] action ,
'sequence' ,
] choice* ;
: 'choice' ( -- parser ) : 'choice' ( -- parser )
'sequence' sp "|" token sp list-of [ 'actioned-sequence' sp "|" token sp list-of [
dup length 1 = [ first ] [ <ebnf-choice> ] if dup length 1 = [ first ] [ <ebnf-choice> ] if
] action ; ] action ;
@ -200,6 +212,7 @@ DEFER: 'choice'
[ [
'non-terminal' [ symbol>> ] action , 'non-terminal' [ symbol>> ] action ,
"=" syntax , "=" syntax ,
">" token ensure-not ,
'choice' , 'choice' ,
] seq* [ first2 <ebnf-rule> ] action ; ] seq* [ first2 <ebnf-rule> ] action ;