2013-05-29 67 views
1

我想修復我的TreeWalker,以便它可以實現不同的字符串模板,具體取決於是否找到括號。字符串模板和句法謂詞

即在下面的公式中:x - (y - z) 使用方括號將會改變公式的值。沒有括號,公式就變成x - y - z這是錯誤的。我正在嘗試使用一個不同的字符串模板來減去和減去一個括號。這些如下:

minus(op1,op2)    ::= "$op1$ - $op2$" 
minusb(op1,op2)    ::= "($op1$ - $op2$)" 

和我正在嘗試使用這些TreeWalker部分如下。這只是一個更大的TreeWalker的一部分。

additiveExpr 
scope { bool aFlag } 
@init {bool aFlag = true; } 
    : ^(PLUS 
      { $additiveExpr::aFlag = false; 
      $formula::mFlag = false; 
      } 
      op1=expression op2=expression) 
     -> {$additiveExpr::aFlag}? 
      plusb(op1={$op1.st},op2={$op2.st}) 
     -> plus(op1={$op1.st},op2={$op2.st}) 
    | ^(MINUS 
      { 
      $additiveExpr::aFlag = false; 
      $formula::mFlag = false; 
      } 
      op1=expression op2=expression) 
     -> {$additiveExpr::aFlag}? 
      minusb(op1={$op1.st},op2={$op2.st}) 
     -> minus(op1={$op1.st},op2={$op2.st}) 

在上述規則中,aFlag總是返回false,產生沒有括號的模板。我很努力地理解爲什麼它有一個括號時不會返回true。

我可以發佈解析器的其他部分,如果這將有所幫助。

我已經計算出條件部分是由句法謂詞決定的。當additiveExpr之前的標記是括號時,我需要語法謂詞表達式爲真(詞法分析器標記OPEN'(')。是否需要從Parser傳遞給TreeWalker,還是可以從此處解決?是等效解析器代碼

absExpr returns [string ret_type] 
    : ABS^ OPEN! additiveExpr CLOSE! 
     {$ret_type = "numeric"; } 
    | additiveExpr 
     {$ret_type = $additiveExpr.ret_type; } 
    ; 

additiveExpr returns [string ret_type] 
    : m=multiplicativeExpr ((PLUS|MINUS)^ multiplicativeExpr)* 
     {$ret_type = $m.ret_type; } 
    ; 

編輯:

最新分析器單元:

absExpr returns [string ret_type] 
    : ABS^ OPEN additiveExpr CLOSE 
     {$ret_type = $additiveExpr.ret_type; } 
    | (OPEN additiveExpr CLOSE)=> OPEN additiveExpr CLOSE 
     {$ret_type = $additiveExpr.ret_type; } 
    | additiveExpr 
     {$ret_type = $additiveExpr.ret_type; } 
    ; 
+0

提示:'[]'是方括號或只是「括號」,'()'是括號,' {}'是花括號或者只是「大括號」,'<>'是尖括號。 –

回答

0

我可能會嘗試像以下,而不是使用語義斷言你只需要確保和不是在您的解析器語法中使用additiveExpr規則中的!運算符,或者OPENCLOSE令牌不會供您的樹型助手使用。

additiveExpr 
    : ^(PLUS OPEN op1=expression op2=expression CLOSE) 
     -> plusb(op1={$op1.st},op2={$op2.st}) 
    | ^(PLUS op1=expression op2=expression) 
     -> plus(op1={$op1.st},op2={$op2.st}) 
    | ^(MINUS OPEN op1=expression op2=expression CLOSE) 
     -> minusb(op1={$op1.st},op2={$op2.st}) 
    | ^(MINUS op1=expression op2=expression) 
     -> minus(op1={$op1.st},op2={$op2.st}) 
    ; 

以前的答案:

這是我很難告訴正是你想要如何工作的。有一兩件事,可能是一個問題是這樣的初始化:

scope { bool aFlag } 
@init {bool aFlag = true; } 

這個聲明具有相同名稱aFlag 2個不同的變量。其中一個將出現在作用域類中,另一個將成爲additiveExpr方法中的局部變量。您的意思是不是要做到這一點,而不是(對ANTLR語法我已經對工作特別是)

scope { bool aFlag } 
@init { $additiveExpr::aFlag = true; } 
+0

它可能在那個區域。在一個簡單的例子中,我試圖翻譯下面的X +(Z - T)。我有一個用於減號/加號的字符串模板和一個用於減號/加號的圓括號。因此,當我的翻譯出現時,我會在所有內容(MACRO(X)+(MACRO(Z) - MACRO(T)))或無括號MACRO(X)+ MACRO(Z) - MACRO(T)上得到圓括號。我希望只有當它們實際存在於我的原始公式中時才能得到括號。 –

+0

@JamesRandles我重寫了我的答案的前半部分。希望這可以幫助你實現它。 :) –

+0

謝謝。我更接近結果。但是,我仍然在解析器部分中掙扎。我已經嘗試了一些選項來將OPEN/CLOSE括號發送給步行者,但我嘗試的選項似乎不能正常工作。我修改了我的問題以包含解析器的最新部分。顯然有些問題,但我不確定如何改變它。 –