私はBisonを初めて使っています。私はパーサーを実装しようとしています。私が直面している主な問題は、解析ツリーです。私は削除することができないツリーに関連するエラーを取得しています。それは "未知の型名"ツリー "と言います。ここにyファイルがあります。誰かがこれを整理するのを手伝ってくれたら嬉しいです。私は非常に悪いパーサーが必要です。前もって感謝します。Bisonを使った構文解析木
%{
#include <stdio.h>
#include <string.h>
void yyerror(const char *str)
{
fprintf(stderr,"error FAIL: %s\n",str);
}
int yywrap()
{
return 1;
}
enum treetype {operator_node, variable_node};
typedef struct tree {
enum treetype nodetype;
union {
struct {struct tree *left, *right; char operator;} an_operator;
char *a_variable;
} body;
} tree;
static tree *make_op (tree *l, char o, tree *r) {
tree *result= (tree*) malloc (sizeof(tree));
result->nodetype= operator_node;
result->body.an_operator.left= l;
result->body.an_operator.operator= o;
result->body.an_operator.right= r;
return result;
}
static void printtree (tree *t, int level) {
#define step 4
if (t)
switch (t->nodetype)
{
case operator_node:
printtree (t->body.an_operator.right, level+step);
printf ("%*c%c\n", level, ' ', t->body.an_operator.operator);
printtree (t->body.an_operator.left, level+step);
break;
case variable_node:
printf ("%*c%c\n", level, ' ', t->body.a_variable);
}
}
%}
%union {
char* a_variable;
tree* a_tree;
}
%start file
%token <a_variable> TOKDIGIT TOKFLOAT TOKID TOKSEMICOLON TOLCOLON TOKCOMMA TOKUNRECOG TOKCOMMENT TOKDOT TOKMINUS TOKCOLON
%type <a_tree> field object file ID
%right TOKMINUS
%%
file :
| object file { printtree($1, 1); }
;
object : field object {$$ = make_op($1, '', $2);}
| field {$$ = $1 ; }
;
field : ID TOKCOLON field {$$ = make_op ($1, ':', $3); }
| ID TOKCOMMA field {$$ = make_op ($1, ',', $3); }
| ID TOKSEMICOLON field {$$ = make_op ($1, ';', $3); }
;
ID : TOKID { $$ = $1; }
;
%%
私はあなたから提案された変更を行いましたが、tab.cファイルをコンパイルしようとすると "unknown type name 'tree'というエラーが表示されます。文法は今のようになります: 'file:/ * empty */{return NULL; } |フィールドファイル{printtree($ 1、1); NULLを返します。 } ; フィールド:ID TOKCOLONフィールド{$$ = make_op($ 1、 ':'、$ 3); } | ID TOKCOMMAフィールド{$$ = make_op($ 1、 '、'、$ 3); } | ID TOKSEMICOLONフィールド{$$ = make_op($ 1、 ';'、$ 3); } |/*空の*/{NULLを返します。 } ; ID:TOKID {$$ = $ 1; } ; ' –
問題は別の場所です。あなたの 'tree' typedef名に関するCプログラミングエラーのように見えます。 'yacc'からエラーメッセージが出ることはありませんか? – Kaz
あなたの 'tree'型はおそらくヘッダファイルで定義されなければなりません。 Yaccが 'YYSTYPE'解析ノード型を生成するために使うYacc'%union'に 'tree'を使います。 'yacc -d'を実行すると、' YYSTYPE'が宣言された 'y.tab.h'ヘッダファイルが生成されます。 '%union'が' tree'型を定義している場合、 'YYSTYPE'は' tree'型のメンバを持ちます。 'y.tab.h'をインクルードする人は' tree'の定義をどこかからインクルードする必要があります。そうでなければ 'YYSTYPE'宣言は未定義の型を参照します。 – Kaz