Hi Roberto,
> Anyway, in the code below the tests C1..C3 and D1..D4 are based in
> your examples. In the block D1..D4 only D4 yields an error, and that
> makes sense to me - but in the block C1..C3 the tests C1 and C3 yield
> errors but C2 does not. Is this behavior of C1..C3 something that is
> explained in the documentation? How? I admit that I'm still struggling
> with some terms, sorry...
>
> The code:
>
> [...]
>
> (Cb"c" ) :pm() -- C1
> (Cb"c":Cg"c") :pm() -- C2
> (Cb"c":Cg"c"):Ct():pm() -- C3
C2 is really subtle. I first thought that was a bug :-)
All three cases are wrong. In C2, however, as the back reference is
inside a named group, the named group just throws away its inner
capture, without evaluating it. The manual allows that:
"Usually, LPeg does not specify when (and if) it evaluates its captures."
As the back reference is not evaluated, no error is raised. (Again, this
highlights that captures are computations; it is hard to express them
statically...)
You know documentation is of high quality when the author consults it to justify program behavior. :)
I would request that the manual be enhanced with:
"Usually, LPeg does not specify if, when, or how many times it evaluates its captures."
It bit me long ago that Cb may reevaluate Ct. I.e.:
Cg(Ct(), "foo") * Cb("foo")
May produce one or two unique tables. An example in the manual like the above would be very useful to communicate that I think.
Please forgive terseness and possibly buggy example code as I'm on my phone.
Patrick