2011-03-03 6 views
3

これはparboiledパーサフレームワークとBNF/PEGの両方に固有の質問です。EBNF/parboiled:regexpをPEGに変換する方法は?

のは、私はあなたが(空白ではない1つまたは複数の文字)空白以外を定義する方法を

<line>    ::= <ws>? <identifier> <ws>? '=' <nonwhitespace> <ws>? 
<ws>     ::= (' ' | '\t' | {other whitespace characters})+ 
<identifier>   ::= <identifier-head> <identifier-tail> 
<identifier-head> ::= <letter> | '_'  
<identifier-tail> ::= (<letter> | <digit> | '_')* 
<letter>    ::= ('A'..'Z') | ('a'..'z') 
<digit>    ::= '0'..'9' 
<nonwhitespace>  ::= ___________ 

の擬似EBNFを表し、かなり単純な正規表現

^\\s*([A-Za-z_][A-Za-z_0-9]*)\\s*=\\s*(\\S+)\\s*$ 

を持っているとしましょうEBNFで?

Java parboiledライブラリに精通している人には、nonwhitespaceを定義するルールをどのように実装できますか?

+0

待ち、以下のとおりです。あなたは、たとえば 空白以外の空白()ルールと一致していない任意の文字として定義されますので、これは、TestNotANYルールを使用して行うことができゆでて

反復量限定子?私が文法を読むことができるところでは、ただ一つの手紙などがあるかもしれません。 – fge

+0

'identifier-tail'を参照してください。 –

+0

ええと、私はEBNF文法でそれを読むようにしていました。 。 – fge

答えて

5

文字範囲と文字範囲の操作を指定するために、字句生成ツールの規則に慣れています。

多くのレクサージェネレータあなたが書くかもしれないので、文字を表すために進値(0xのようなものを)受け入れる:数字のため

'0'..'9' 
0x30..\0x39 

を。

非ホワイトスペースの場合は、使用している文字セットを知る必要があります。 7ビットのASCIIの場合は、空白以外は、概念的に、すべての印刷文字:ISO8859-1用

0x21..\0x7E 

(0x21..\0x7E | 0x80-0xFF) 

は0x80以上の文字コードはスペースやされない場合は、自分で決めることができます(非です - 壊れた空間と宇宙?)。また、制御文字0x0..0x1Fの状態についても決定します。タブ(0x9)は空白文字ですか? CR 0xDとLF 0xAはどうですか? ETBの制御文字はどうですか?

ユニコードは、その巨大なセットであり、あなたのリストが大きくて面倒なので、より難しいです。 C'est la vieDMS Software Reengineering Toolkitは、多種多様な言語のパーサーを構築するために使用され、ASCII用のレクサー、ロットのz用のISO8859-z、およびUnicodeをサポートしなければなりません。複雑な「添加物」の正規表現の範囲を記述するのではなく、DMSは、サブトラクティブ正規表現を可能にし、私たちは書くことができます。

<UniCodeLegalCharacters>-<UniCodeWhiteSpace> 

理解する方がはるかに簡単で、右の最初の試行でそれを取得しています。

私は単に空白ではない任意の文字として空白以外を定義するEBNFで
2

:これは、あなたが可能なシンボルの全範囲を定義する「anycharacter」リテラル、および明確な定義を持っていることが必要です

nonwhitespace ::= anycharacter - whitespace 

その中の文字は空白です。

Sequence(TestNot(WhiteSpace()) , ANY)