[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: Distributivity parsing, prompt symbol and line editing
From: |
Hans Aberg |
Subject: |
Re: Distributivity parsing, prompt symbol and line editing |
Date: |
Wed, 7 Jul 2004 18:52:26 +0200 |
At 02:25 +0200 2004/07/07, Andrej Prsa wrote:
>Also, if it's not a problem, could you please comment on my naive way of
>implementing a prompt with:
>
>input : /* empty */
> | input line { printf ("> "); }
>
>Finally, if I haven't completely exhausted your patience, is there any
>portable way to have at least minimal line editing capability (cursor
>movement, history, ...) in interactive mode?
Bison is not good at generating an interactive interpreter, as one does not
know when the reductions take place: It depends whether the parser thinks
it needs a lookahead token or not.
Therefore, I implemented a parser as though it should one full file. In
order to create a REP loop, I then made a specially written loop, which
reads one line (or whatever input) at a time, and then invoked the parser
after that, printing out the result.
>I'm a total newbie (since two days ago) and I've been struggling with
>flex/bison to write a small scripting language. Now I have come to a solid
>wall where several hours of documentation-flipping hadn't helped. This is
>my problem:
>
>All input lines start with a directive (which is an ordinary word)
>followed by one or more comma-separated arguments, e.g.
>
> directive arg1, arg2, ..., argN '\n'
>
>The directive itself acts only on one argument, so the above line should
>reduce (well, not really reduce, distribute really) to:
>
> directive arg1 '\n'
> directive arg2 '\n'
> . . .
> directive argN '\n'
>
>Now I wonder: is this a job for a scanner or a parser?
If there is a distinction say between a single \n (NEWLINE) and more \n
(PARAGRAPH), then let the lexer decide that. Otherwise, it looks as though
putting it on the parser is the best.
> I tried something
>like this for the bison file (I'm giving only the relevant parts):
>
>input : /* empty */
> | input line { printf ("> "); }
> ;
>line : '\n' /* Is it an empty line? */
> | d_line /* Is it a directive? */
> ;
>d_line : h_line '\n'
> ;
>h_line : HELP arglist
> ;
>arglist : /* no arguments */ { printf ("no args.\n"); }
> | STRARG { printf ("%s\n", $1); }
> | arglist ',' STRARG { printf ("%s\n", $3); }
> ;
There are two techniques you can use here: If your directives are known at
cvomiple time, and few, then you can put them in the Bison grammar.
Otherwise, one can also create a look-up table: The lexer will identify a
token, check it in the lookup table, return the token DIRECTIVE as well the
type of directive found in the lookup table.
%token NEWLINE "\\n"
%token DIRECTIVE "directive"
...
%%
...
d_line:
DIRECTIVE "\\n"
;
directive:
HELP arglist
| FOO arglist
...
| DIRECTIVE arglist { /* compute function for directive found */ }
;
...
This way you can handle directives with different types of arguments.
>My question is now this: what would be the proper way to implement
>distributivity reduction?
What do you mean by this.
> Or should I define a global string variable
>carrying the directive name and call the appropriate handling function?
You can use whatever you find convenient for you program: One can let the
lexer return numbers, strings, function pointers, etc. ftne one has to
change method as the program becomes more advanced. So, for a start, settle
for something that is easy to implement.
Hans Aberg