emacs-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Make peg.el a built-in library?


From: Stefan Monnier
Subject: Re: Make peg.el a built-in library?
Date: Thu, 30 Sep 2021 15:44:28 -0400
User-agent: Gnus/5.13 (Gnus v5.13) Emacs/28.0.50 (gnu/linux)

> Whether or not PEG gets added to core I'd like to propose some patches.
> The "peg-doc-patches.diff" attachment adds some documentation to the
> Commentary section, including an example grammar based on a
> much-simplified version of what gnus-search does.

Looks great, thanks.

> The peg-allow-symbols patch is more tentative. The issue is that _all_
> of the entry-points to peg code are macros, meaning you can't build your
> grammar up in a variable, and then pass that variable to any of
> `peg-run', `peg-parse', `with-peg-rules', etc. Nobody will evaluate the
> variable; you have to literally write the rules inside the
> `with-peg-rules' form. It seems like a fairly plausible use-case to
> store the rules in a variable or an option, even if you're not doing
> run-time manipulation of them. The only solution, as Adam found with
> org-ql, is to `eval' one of the macros.
>
> This doesn't seem necessary! The patch has `with-peg-rules' check if the
> rules are a symbol, and take the `symbol-value' if so. But I wonder if
> it wouldn't be nicer to break some of the code out: `peg-normalize'
> seems to be the entry-point for "compile this grammar", and that could
> be modified to work the way that some languages provide for pre-compiled
> regexps: a way to let the developer build and compile the grammar at
> load-time or launch-time, then feed the stored compiled version to
> parsing routines.

`peg` is the macro that's supposed to be this compilation step: you pass
it a PEX and you receive a value in return.  It's a bit like `lambda`.

You can then use this value (a "peg matcher") to parse something by
passing it to `peg-run`.

So you can do

    (let ((parser (peg PEX)))
      ...
      (peg-run parser ...)
      ...)

What might still be missing, tho is a way to invoke this `parser` from
within a PEX.  So we might want to add a new PEX form that would be akin
to `funcall`.  We could name it `call`:

    (let* ((parser (peg PEX))
      ...
      (with-peg-rules
          ((foo ...)
           (bar ... (call parser) ...)
           (baz ...))
        ...))

so (peg-parse (call FORM)) would end up equivalent to (peg-run FORM ...).
WDYT?


        Stefan




reply via email to

[Prev in Thread] Current Thread [Next in Thread]