Question

Avec Bison, j’ai compris comment tout rassembler dans une longue chaîne, comme suit:

arg_list:
    WORD arg_list { strcat( $1, "IFS" ); $ = strcat($1, $2); }  |
    WORD
    ;

et:

WORD arg_list { printf("%s, %s\n", $1, $2); }

Mais le problème est que je devrai alors diviser à nouveau 2 $ dans la deuxième règle pour l’analyser. Existe-t-il un moyen de remplir un tableau au lieu d'utiliser simplement la concaténation? Est-ce que je m'y prends mal?

Si j'ai besoin de construire quelque chose comme une liste chaînée qui pourrait avoir un sens, je ne sais pas quel serait le bon moyen de se lier à arg_list, puis de nettoyer la mémoire.

Était-ce utile?

La solution

Si vous avez un type de tableau avec une opération push_front, il s'agit trivialement:

arg_list:
    WORD arg_list { $ = $2.push_front($1); }
    WORD { $ = new Array<string>($1); }

sans cela, cela demande plus de travail. Vous pouvez utiliser un vecteur et ajouter les chaînes à la fin (qui seront dans l'ordre inverse). Ou vous pouvez utiliser une liste chaînée (ce qui est plus facile si vous utilisez straight C):

arg_list:
    WORD arg_list { $ = malloc(sizeof(struct list_elem));
                    $->next = $2;
                    $->val = $1; }
    WORD          { $ = malloc(sizeof(struct list_elem));
                    $->next = 0;
                    $->val = $1; }

Autres conseils

%union {
  char *char_ptr;
}
%token STRING
%type <char_ptr> STRING string
%%
...
string:
    STRING        /* Lexic analyzer return STRING and set yylval = yytext; */
  | string STRING
    { char *str = (char*) malloc(strlen($1) + strlen($2) + 1);
      strcpy(str, $1);
      strcat(str, $2);
      free($2);
      free($1);
      $ = str;
    }
  ;
%%
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top