2017-04-05 117 views
0

因此,我正在使用ANTLRWorks 2.1在ANTLR4中使用組合語法。我有詞法規則IdentifierBlock,這些規則不被識別爲定義的詞法分析器規則,但僅在最後一個定義的分析器規則中。這些規則刪除(或隱藏)這些錯誤後添加一個文字。ANTL 4 Lexer規則無法在組合語法中識別

我,並在最後的錯誤語法(斜體令牌引發錯誤):

grammar GCombined; 

options { language = Cpp; } 

@lexer::namespace{AntlrTest01} 
@parser::namespace{AntlrTest01} 

    /* First Lexer Stage */ 

Bit: '0' | '1'; 
Digit : '0'..'9'; 
ODigit: '0'..'7'; 
XDigit: '0'..'f'; 
Letter: ('a'..'z') | ('A'..'Z'); 
Symbol: '|' 
     | '-' 
     | '!' 
     | '#' 
     | '$' 
     | '%' 
     | '&' 
     | '(' 
     | ')' 
     | '*' 
     | '+' 
     | ',' 
     | '-' 
     | '.' 
     | '/' 
     | ':' 
     | ';' 
     | '<' 
     | '=' 
     | '>' 
     | '?' 
     | '@' 
     | '[' 
     | ']' 
     | '^' 
     | '_' 
     | '`' 
     | '{' 
     | '|' 
     | '}' 
     | '~'; 
WSpace: (' ' 
     | '\t' 
     | '\r' 
     | '\n' 
     | '\c' 
     | '\0' 
     | '\u000C' 
     )+ -> skip; 

DNumber: Digit+; 
ONumber: '0o' Digit+; 
XNumber: '0x' Digit; 
Integer: DNumber 
     | ONumber 
     | XNumber; 
Float: DNumber '.' DNumber; 

Character: Letter 
     | Digit 
     | Symbol 
     | WSpace; 
String: Character+; 
Literal: '"' String '"'; 

Boolean: 'true' | 'false'; 

    /* Second Lexer Stage */ 

Number: Integer | Float; 
Identifier: Letter (Letter | Digit | '_')+; 
Keyword: Letter+; 
Operator: '+' 
     | '-' 
     | '*' 
     | '/' 
     | '%' 
     | '==' 
     | '!=' 
     | '>' 
     | '<' 
     | '>=' 
     | '<=' 
     | '&&' 
     | '||' 
     | '^' 
     | '&' 
     | '|' 
     | '<<' 
     | '>>' 
     | '~' ; 

Expression: (Operator | Identifier) 
     '(' (Identifier | Number)+ ')'; 
Parameter: Identifier 
     | Expression 
     | Number; 
Statement: Keyword '(' Parameter+ ')'; 
Block: '{' Statement+ '}'; 

    /* Third Lexer Stage */ 

Add: '+'; 
Sub: '-'; 
Mlt: '*'; 
Div: '/'; 
Mod: '%'; 
Mathop: Add | Sub | Mlt | Div | Mod; 

Deq: '=='; 
Neq: '!='; 
Gtr: '>'; 
Lss: '<'; 
Geq: '>='; 
Leq: '<='; 
Condop: Deq | Neq | Gtr | Lss | Geq | Leq; 

And: '&&'; 
Or: '||'; 
Xor: '^'; 
Bnd: '&'; 
Bor: '|'; 
Logop: And | Or | Xor | Bnd | Bor; 

Neg: '!'; 
Boc: '~'; 
Negop: Neg | Boc; 

Asl: '<<'; 
Asr: '>>'; 
Shftop: Asl | Asr; 

Eql: '='; 

Inc: '++'; 
Dec: '--'; 
Incop: Inc | Dec; 

Peq: '+='; 
Meq: '-='; 
Teq: '*='; 
Seq: '/='; 
Req: '%='; 
Casop: Peq | Meq | Teq | Seq | Req; 

Lparen: '('; 
Rparen: ')'; 
Lbrack: '['; 
Rbrack: ']'; 
Lbrace: '{'; 
Rbrace: '}'; 
Point : '.'; 
Colon : ':'; 

Numvar: Number 
     | Identifier 
     | Mathop '(' Parameter+ ')'; 
Boolvar: Boolean 
     | Identifier 
     | Condop '(' Parameter+ ')' 
     | Logop '(' Parameter+ ')'; 
Metaxpr: (Identifier | Operator) '(' Parameter+ ')'; 

    /* First Parser Stage */ 

    //expressions 

add: '+' '(' Numvar+ ')'; 
sub: '-' '(' Numvar+ ')'; 
mlt: '*' '(' Numvar+ ')'; 
div: '/' '(' Numvar+ ')'; 
mod: '%' '(' Integer+ ')'; 
mathexpr: add 
     | sub 
     | mlt 
     | div 
     | mod; 

eql: '==' '(' Parameter+ ')'; 
neq: '!=' '(' Parameter+ ')'; 
gtr: '>' '(' Parameter+ ')'; 
les: '<' '(' Parameter+ ')'; 
geq: '>=' '(' Parameter+ ')'; 
leq: '<=' '(' Parameter+ ')'; 
condexpr: eql 
     | neq 
     | gtr 
     | les 
     | geq 
     | leq; 

and: '&&' '(' Parameter+ ')'; 
or : '||' '(' Parameter+ ')'; 
xor: '^' '(' Parameter+ ')'; 
bnd: '&' '(' Parameter+ ')'; 
bor: '|' '(' Parameter+ ')'; 
logexpr: and 
     | or 
     | xor 
     | bnd 
     | bor; 

asl: '<<' '(' Parameter Numvar ')'; 
asr: '>>' '(' Parameter Numvar ')'; 
shiftexpr: asl | asr; 

neg: '!' '(' Parameter ')'; 
boc: '~' '(' Parameter ')'; 
negexpr: neg 
     | boc; 

arrexpr: Identifier '[' Numvar ']'; 

    //instruction forms 

vardec: 'def' '(' Identifier+ ')' ': ' Identifier ; 
lindec: Identifier '(' Identifier ')'; 
assign: '=' '(' (Identifier | lindec) Parameter ')'; 

incstmt: (Inc | Dec) '(' Identifier ')' 
     | Casop '(' Identifier Identifier ')'; 

cond: 'if' '(' Boolvar ')' Block 
    ('else if' '(' Boolvar ')' Block)? 
    ('else' Block)?; 

loop: (
     ('while' '(' (condexpr | negexpr) ')') 
    | ('for' '(' assign ',' (condexpr | negexpr) ',' incstmt')') 
    ) Block; 

fundef: 'func' '(' Identifier Parameter+ ')' ': ' Identifier Block; 
prodef: 'proc' '(' Identifier Parameter* ')' Block; 
call: Identifier '(' Parameter+ ')'; 

excHandler: 'try' Block 
      'catch' '(' Identifier ')' Block 
      ('finally' Block)?; 

classdef: 'class' '(' Identifier ')' (': ' _Identifier_)? _Block_; 
+1

需要提供演示錯誤的完整語法。 – GRosenberg

回答

0

ANTLR需要明確的語法規則。在提供的語法中,Symbol規則與Operator規則和其他規則衝突。 IdentifierLetter規則衝突。規則衝突時,他們可以匹配相同的輸入(內容&長度)。

另外,例如,Symbol規則包括'{'作爲alt。後續使用文字'{'(這是一種隱式標記類型)的規則將不匹配,因爲隱式標記類型與Symbol標記類型不同。最佳做法是避免重複使用文字 - 在規則中定義文字,然後引用該規則。

最好的建議是購買TDAR的副本來學習Antlr4。

+0

我一直在閱讀教程和編碼。你看。逆轉詞法分階段的順序解決了問題! –

+0

通過重新排列,其他衝突規則現在無法按預期工作! Antlr沒有處理含糊不清的問題 - 它只是(總是)使用第一個衝突規則(自上而下),其結果是功能上隱藏了剩下的內容。 – GRosenberg