2017-12-22 35 views
1

私はbisonとflexを使用して、(将来のどこか)抽象構文木(AST)を作成しています。今のところ、私は算術式(例えば+を使って)だけを持っていますが、式 - >式 '+'式|定数ですが、式には2つの属性、つまりコード(ルールの右側の最初の要素(RHS)の値を持つ文字列、+と2番目の式の値)が必要です。属性付きBison複数の非終端記号

私は次の構造を作成:文字列が(今のところ、私はちょうどそれらを印刷したい)としてそれらの両方を保持する

%union { 
    struct{ 
     char* code; 
     char* varn; 
    } attributes; 

    int intval; 
} 

を。文法と共に トークンと項目は以下のように定義される:Flexで

%token <intval> CONST 
%type <attributes> expr 

%% 
expr: 
    expr '+' expr 
    { 
     printf("%s ",$1.val); 
     printf("%s \n",$3.val); 
     printf("code: %s %s\n",$1.code,$3.code); 
    } 
expr: 
    CONST 
    { 
     int source=$1; 
     char temp[100]; 
     sprintf(temp, "%d", source); 
     $$.val=strcat(temp,"1"); 
     $$.code=temp; 
     printf("val for %d is %s; code is %s\n",$1,$$.val,$$.code); 
    } 

%% 

、Iは、(SO 4のvalが4になる)要素自体にCONSTの値(INTVAL)を設定しました。 2番目のルールが適用されると、プログラムは値を正しく出力します。しかし、最初のものが適用されたとき(全体が印刷されるとき)、両方の式は同じvalを持ちます。

varn for 4 is 41; code is 41 
varn for 5 is 51; code is 51 
51 51 
code: 51 51 

(1だけで何かをテストするために追加されたこと、それは計画の一部ではありません)

私はなぜ正確に把握することはできません。 exprがint型に変更された場合

%type <intval> expr 

正しく動作します。あなたのコードが何をしているか

+0

'$$。code = temp'は非常に疑わしいようです - ' temp'の有効範囲は何ですか?おそらくそれはすべての '$$。code'が同じ値を指していることを意味していますか? –

+0

$ 1のint値を文字列に変換しようとしているので、$$。codeにchar *を割り当てることができます。私もいくつかのポインタのためにそれだと思っていましたが、私は長い間Cで作業していませんでした。これが私がその変換を行う唯一の方法でした。 tempはintからstringへ変換された値を格納するための一時変数として使用されました($$。コードをsprintfで直接使用しようとするとエラーが発生しました) – tudors5

+0

おそらく '$$。code = strdup(temp);'適切なポイントに割り当てられたメモリを「解放する」ことを覚えておいてください。 –

答えて

0

は以下にすぎ異ならないです:あなたは出力が「世界の世界」買ってあげるよう

char temp[100]; 

strcpy(temp,"hello"); 
char *str1=temp; 

strcpy(temp,"world"); 
char *str2=temp; 

printf("%s %s\n",str1,str2); 

str1str2の両方がメモリ内の同じポイントで指しています。メモリ内に独自の場所を持つように、各文字列にメモリを割り当てる必要があります。

そして、 "expr '+' expr"パターンでは、それぞれの文字列をfreeとし、新しいものを作成して解析チェーンを渡します。

+0

わかりました。ありがとう! – tudors5