For these questions, you really need to get the code & play with it.
* Alter the associativity and precedence of the operators in $8.2 and generate the resulting parse trees.
I would rewrite the yacc to use %left etc., so it is easy to modify the precedence etc.:
%left '+' '-' %left `*` `/` %% input : exp {printtree ($1, 1);} ; exp : '+' exp {$$ = $2;} | '-' exp {$$ = make_operator (NULL, '~', $2);} | exp '+' exp {$$ = make_operator ($1, '+', $3);} | exp '-' exp {$$ = make_operator ($1, '-', $3);} | exp '*' exp {$$ = make_operator ($1, '*', $3);} | exp '/' exp {$$ = make_operator ($1, '/', $3);} | number {$$ = make_number ($1);} | variable {$$ = make_variable ($1);} | '(' exp ')' {$$ = $2;} ;
+ Add extra language features (e.g. function calls, array accesses, conditional expressions) to the grammar in $8.2 and build the corresponding parse trees.
e.g. simple function calls:
enum treetype {operator_node, number_node, variable_node, call_node}; typedef struct tree { enum treetype nodetype; union { struct {struct tree *left, *right; char operator;} an_operator; struct {struct tree *func, *param;} a_call; int a_number; char a_variable; } body; } tree; static tree *make_call (tree *f, tree *p) { tree *result= (tree*) malloc (sizeof(tree)); result->nodetype= call_node; result->body.a_call.func= f; result->body.a_call.param= p; return result; } factor : number {$$ = make_number ($1);} | variable {$$ = make_variable ($1);} | '(' exp ')' {$$ = $2;} | variable '(' exp ')' {$$ = make_call ($1, $3);} ;
Although it would be better to allow a variable number of parameters (c.f. lab ex 6)
e.g. a (b, c)
call / \ a b \ c