1

antlr3 で文法のような検索エンジンを解析するための文法を作成することは、私が助けを必要とする作業です。

グラマーは以下を許可する必要があります。

  • 用語間の AND の省略: 例 犬 猫 = 犬 AND 猫
  • AND は OR よりも優先する必要があります: 猫 犬 または ボート = (猫 AND 犬) または ボート
  • 括弧内の用語の任意のカプセル化 : 猫 OR( 犬 and (魚 牛) OR 鳥)

上記のすべての基準を実装することは、(私にとって) 挑戦です。私の文法を見て、すべての基準を適切に満たすことができなかったため、アドバイスのエラーと修正を行ってください。

文法

tokens {
FOR;
END;
FIELDSEARCH;
TARGETFIELD;
RELATION;
ANDNODE;
}
startExpression  : orEx;

expressionLevel4    
: LPARENTHESIS! orEx RPARENTHESIS! | atomicExpression;

expressionLevel3    
: (fieldExpression) | expressionLevel4 ;

expressionLevel2    
: (nearExpression) | expressionLevel3 ;

expressionLevel1    
: (countExpression) | expressionLevel2 ;

notEx   : (NOT^)? expressionLevel1;

andEx   : (notEx        -> notEx)
(AND? a=notEx -> ^(ANDNODE $andEx $a))*;

orEx    : andEx (OR^  andEx)*;

countExpression  : COUNT LPARENTHESIS WORD RPARENTHESIS (LESSTHEN|MORETHEN) EQUAL? NUMBERS -> ^(COUNT WORD ^(RELATION LESSTHEN? MORETHEN? EQUAL?) NUMBERS);

nearExpression  : NEAR^ LPARENTHESIS! (WORD|PHRASE) MULTIPLESEPERATOR! (WORD|PHRASE) MULTIPLESEPERATOR! NUMBERS RPARENTHESIS!;

fieldExpression : WORD PROPERTYSEPERATOR WORD -> ^(FIELDSEARCH ^(TARGETFIELD WORD));

atomicExpression 
: WORD
| PHRASE ;


LPARENTHESIS : '(';
RPARENTHESIS : ')';

LESSTHEN : '<';
MORETHEN : '>';
EQUAL : '=';

AND    : ('A'|'a')('N'|'n')('D'|'d');
OR     : ('O'|'o')('R'|'r');
ANDNOT : ('A'|'a')('N'|'n')('D'|'d')('N'|'n')('O'|'o')('T'|'t');
NOT    : ('N'|'n')('O'|'o')('T'|'t');
COUNT:('C'|'c')('O'|'o')('U'|'u')('N'|'n')('T'|'t');
NEAR:('N'|'n')('E'|'e')('A'|'a')('R'|'r');
PROPERTYSEPERATOR : ':';
MULTIPLESEPERATOR : ',';

fragment NUMBER : ('0'..'9');
fragment CHARACTER : ('a'..'z'|'A'..'Z'|'0'..'9'|'*'|'?');
fragment QUOTE     : ('"');

fragment SPACE     : ('\u0009'|'\u0020'|'\u000C'|'\u00A0');

//fragment UNICODENOSPACES  :  ('\u0000'..'\u0008'|'\u0010'..'\u0019'|'\u0021'..'\009F'|'\u00A1'..'\009F');
fragment UNICODENOSPACES  :  ('\u0021'..'\u0039'|'\u003B'..'\u007E'|'\u00A1'..'\uFFFF');

WS     : (SPACE) { $channel=HIDDEN; };
NUMBERS : (NUMBER)+;
PHRASE : (QUOTE)(CHARACTER)+((SPACE)+(CHARACTER)+)+(QUOTE);
WORD   : (UNICODENOSPACES)+;

入力が与えられた場合:

title:cats AND  fish OR Bird AND (bird and dirt) OR (bart or title:bard OR bird AND title:dort)

この AST が作成されます。WORD 用語でキャプチャされた ( ) に注意してください。 ここに画像の説明を入力

他のエラーや間抜けな実装の詳細がある可能性があります。antlrを使用するのは初めてです。

4

1 に答える 1

1

初めての ANTLR で、あなたは良い仕事以上のことをしました。

トークンに'('and')'があるという事実は、範囲に括弧が含まれているためです。ANTLR の字句解析器は貪欲に文字を照合し、可能な限り (!) 一致しようとします最後のルール (可能な限り多くの文字を一致させる) により、2 つのトークン (aと a ) ではなく、 (aトークン)のような入力から 1 つのトークンを作成します。一致する必要があるものに括弧が含まれていないことを確認してください。WORD'\u0021'..'\u0039'"(bird"WORDLPARENTHESISWORDWORD

あなたの文法をコピーして次のように変更WORDすると:

WORD : CHARACTER+;

入力は次のように解析されます。

ここに画像の説明を入力

編集

用語の通常の部分として括弧を使用することは可能ですか? 例: blabla(bla( a)blabla を 2 つの WORDS として認識しますか? パーサーは、括弧がサブタームを導入するのか、それとも WORD を形成する通常の文字なのかを判断する必要があります。

およびの括弧が a の一部ではなく、式の一部であると仮定すると、レクサーレベルで次のように実行できます。(a......a)WORD

WORD : UNICODENOSPACES ((UNICODENOSPACES | '(' | ')')* UNICODENOSPACES)?

a 内の括弧のみWORDが許可されるようになりました。(aの末尾の aも有効にすることで、さらに先に進むことができますがWORD、それが良い考えかどうかはわかりません。

于 2012-11-28T18:42:26.090 に答える