2012-04-09 63 views
0

我有以下的語法解析器(這是一個小樣本):Bison分析器不會前瞻令牌

expr: 
     ident assignop expr 
     { 
      $$ = new NAssignment(new NAssignmentIdentifier(*$1), $2, *$3); 
     } | 
     STAR expr %prec IDEREF 
     { 
      $$ = new NDereferenceOperator(*$2); 
     } | 
     STAR expr assignop expr %prec IDEREF 
     { 
      $$ = new NAssignment(new NAssignmentDereference(*$2), $3, *$4); 
     } | 
     ... ; 

... 

assignop: 
     ASSIGN_EQUAL | 
     ASSIGN_ADD | 
     ASSIGN_SUBTRACT | 
     ASSIGN_MULTIPLY | 
     ASSIGN_DIVIDE ; 

現在我試圖解析以下任何行:

*0x8000 = 0x7000; 
*mem = 0x7000; 

但是,Bison不斷看到「* mem」並減少了「STAR expr」規則,並且未執行預測以查看「STAR expr assignop ...」是否匹配。據我瞭解Bison,它應該做這個預測。我最接近的猜測是,%prec會關閉前瞻或類似的東西,但我不明白爲什麼會這樣做(因爲prec值相同)。

在這種情況下,我如何使它看起來超前?

編輯:

,它進入遇到當「明星EXPR」的狀態是:

state 45 

    28 expr: STAR expr . 
    29  | STAR expr . assignop expr 
    35  | expr . binaryop expr 

    $default reduce using rule 28 (expr) 

    assignop go to state 81 
    binaryop go to state 79 

所以我不明白爲什麼它撿$默認情況下它可以挑選assignop(注在這種情況下,parser.y文件中規則的順序不會影響它選擇哪一個;我嘗試在標準'STAR expr'之上重新排序assignop')。

回答

0

我結束了創建另一個規則「DEREF」像這樣解決這個問題:

deref: 
     STAR ident 
     { 
      $$ = new NDereferenceOperator(*$<ident>2); 
     } | 
     STAR numeric 
     { 
      $$ = new NDereferenceOperator(*$2); 
     } | 
     STAR CURVED_OPEN expr CURVED_CLOSE 
     { 
      $$ = new NDereferenceOperator(*$3); 
     } | 
     deref assignop expr 
     { 
      if ($1->cType == "expression-dereference") // We can't accept NAssignments as the deref in this case. 
       $$ = new NAssignment(new NAssignmentDereference(((NDereferenceOperator*)$1)->expr), $2, *$3); 
      else 
       throw new CompilerException("Unable to apply dereferencing assignment operation to non-dereference operator based LHS."); 
     } ; 

在「expr的」用一個單一的「DEREF」更換兩個規則。

0

如果IDREFASSIGN_EQUAL優先,ASSIGN_ADD等。特別是較高的,在這種情況下,與原解析器(優先級被應用於前)會出現這種情況,你有移位/減少expr: STAR expr規則和各種ASSIGN_ XXX之間的衝突令牌。優先規則解決了所有有利於減少的衝突。

該狀態下的assignop是轉到,而不是轉移或減少,所以根本不進入前瞻或標記處理 - gotos只發生在某個標記移位後,然後減少到非有問題的終端。

+0

糟糕!我想我已經刪除了這個問題,因爲我已經解決了它。我現在更好地回答我的答案... – 2012-04-09 05:31:41