2012-08-27 46 views
3

我在寫一個支持任意布爾表達式的語法。語法用來表示一個程序,稍後通過靜態分析工具。靜態分析工具有一定的侷限性,所以我想申請以下重寫規則:ANTLR重寫規則中的替代

嚴格的不平等近似用小量:

expression_a != expression_b -> expression_a > expression_b || expression_a < expression_b 

expression_a > expression_b -> expression_a >= expression_b + EPSILON 

不平等正在使用「或」語句近似

使用ANTLR有沒有簡單的方法來實現它?目前我的語法如下:

comparison   : expression ('=='^|'<='^|'>='^|'!='^|'>'^|'<'^) expression; 

我不知道如何應用不同的重寫規則,這取決於操作符是什麼。根據上面定義的規則,如果運算符是(「==」,「< =」或「> =」),並且要遞歸地轉換它,我希望樹保持原樣。

回答

3

[...]和遞歸地改造它,否則,[...]

可以部分地做到這一點。

你不能告訴ANTLR改寫a > b^('>=' a ^('+' b epsilon)),然後定義a != b成爲^('||' ^('>' a b) ^('<' a b)),然後讓ANTLR自動重寫既^('>' a b)^('<' a b)分別^('>=' a ^('+' b epsilon))^('<=' a ^('-' b epsilon))

這裏需要一些手動工作。訣竅是,如果此標記未實際解析,則不能僅使用像>=這樣的標記。解決方案是使用imaginary tokens

甲快速演示:

grammar T; 

options { 
    output=AST; 
} 

tokens { 
    AND; 
    OR; 
    GTEQ; 
    LTEQ; 
    SUB; 
    ADD; 
    EPSILON; 
} 

parse 
: expr 
; 

expr 
: logical_expr 
; 

logical_expr 
: comp_expr ((And | Or)^ comp_expr)* 
; 

comp_expr 
: (e1=mult_expr -> $e1) (Eq e2=mult_expr -> ^(AND ^(GTEQ $e1 $e2) ^(LTEQ $e1 $e2)) 
         | LtEq e2=mult_expr -> ^(LTEQ $e1 $e2) 
         | GtEq e2=mult_expr -> ^(GTEQ $e1 $e2) 
         | NEq e2=mult_expr -> ^(OR ^(GTEQ $e1 ^(ADD $e2 EPSILON)) ^(LTEQ $e1 ^(SUB $e2 EPSILON))) 
         | Gt e2=mult_expr -> ^(GTEQ $e1 ^(ADD $e2 EPSILON)) 
         | Lt e2=mult_expr -> ^(LTEQ $e1 ^(SUB $e2 EPSILON)) 
         )? 
; 

add_expr 
: mult_expr ((Add | Sub)^ mult_expr)* 
; 

mult_expr 
: atom ((Mult | Div)^ atom)* 
; 

atom 
: Num 
| Id 
| '(' expr ')' 
; 

Eq : '=='; 
LtEq : '<='; 
GtEq : '>='; 
NEq : '!='; 
Gt : '>'; 
Lt : '<'; 
Or : '||'; 
And : '&&'; 
Mult : '*'; 
Div : '/'; 
Add : '+'; 
Sub : '-'; 
Num : '0'..'9'+ ('.' '0'..'9'+)?; 
Id : ('a'..'z' | 'A'..'Z')+; 
Space : ' ' {skip();}; 

從語法生成的解析器上面將產生以下:


a == b

enter image description here


a != b

enter image description here


a > b

enter image description here


a < b

enter image description here


+0

非常感謝!不知道你可以在一個語句中使用多個重寫規則。 (順便說一下,你如何生成這些圖表?ANTLRWorks?) –

+0

@cheshire,不客氣。是的,AST圖像來自ANTLRWorks的調試器(不是解釋器!)。你也可以通過代碼生成它們,看看這個問答:http://stackoverflow.com/questions/2856612/visualizing-an-ast-created-with-antlr-in-a-net-environment –