2012-08-31 6 views
9

私はANTLRのJavaScript文法(インターネットからのものです)を持っています。これは正規表現のリテラルを除いてすべてをサポートしているようです。ANTLRでJavaScript正規表現を解析する

リテラル正規表現での問題は、あなたが基本的に2つのルール、持っていることです:。

multiplicativeExpression 
    : unaryExpression (LT!* ('*' | '/' | '%')^ LT!* unaryExpression)* 

とルールRegexLiteralCharが通常の表現とは異なるレクサールールを使用しています

regexLiteral 
    : '/' RegexLiteralChar* '/' 

を(例えばA二重引用符はそれを終了しません)。

これは、何らかの形で、パーサーからある種のレクサー状態を変更する必要があることを意味します。これどうやってするの?それも可能ですか?

+1

通信とレクサールールは不可能です。おそらく正規表現リテラルを扱うように見えるこの文法を見てください:http://research.xebic.com/es3/(ZIPファイルをチェックしてください)。 –

答えて

5

バートKiers hereによってコメントで述べた文法を見ると、あなたがこのコメントを見ることができ、

この文法を定義する際に直面する大きな課題があった。

-1- DIVを取り巻くあいまい乗法式と正規表現リテラルに関連してサインします。これは、 のレクサー駆動の魔法で解決されました。ゲーテッドセマンティク述語 は、RegularExpressionsEnabledプロパティの 値に基づいて、正規表現の認識をオンまたはオフにします。規則的な 式が有効になっている場合は、除算よりも優先されます。 正規表現が有効かどうかの決定は、前のトークンが除算の左側のオペランドの最後のトークンであると考えられるヒューリスティックスに基づいて です。

...

areRegularExpressionsEnabled()関数は

private final boolean areRegularExpressionsEnabled() 
{ 
    if (last == null) 
    { 
     return true; 
    } 
    switch (last.getType()) 
    { 
    // identifier 
     case Identifier: 
    // literals 
     case NULL: 
     case TRUE: 
     case FALSE: 
     case THIS: 
     case OctalIntegerLiteral: 
     case DecimalLiteral: 
     case HexIntegerLiteral: 
     case StringLiteral: 
    // member access ending 
     case RBRACK: 
    // function call or nested expression ending 
     case RPAREN: 
      return false; 
    // otherwise OK 
     default: 
      return true; 
    } 
} 

、として定義され、その関数がRegularExpressionLiteral式で使用され、パーサー間

RegularExpressionLiteral 
    : { areRegularExpressionsEnabled() }?=> DIV RegularExpressionFirstChar RegularExpressionChar* DIV IdentifierPart* 
    ; 
関連する問題