develooper Front page | perl.perl5.porters | Postings from December 1999

Re: [ID 19991130.003] Assignment to List Breaks \G.

Thread Previous | Thread Next
December 1, 1999 13:09
Re: [ID 19991130.003] Assignment to List Breaks \G.
Message ID:

Ronald J Kimball writes:
> This is the expected behavior for m//g in a list context.  The regular
> expression is applied repeatedly until it no longer matches, and the
> return value is a list of all the substrings matched.  After the final
> application of the regex, which fails to match, pos() is reset to the
> beginning of the string.

Hi, thanks for all the replies.  Having put -Dr to good use I fully
understand what is happening with my example script.  However, I'd like
to put a case forward that this behaviour is broken and judging from
Randal's question in

there might be others that agree.

Normally, the use of context in Perl to `do the right thing' works well.
I'd suggest that the overloading of /g based on context allows only two
alternatives (/g and no /g) to be selected from a larger desired set of

If I want to match many times, possibly leaving pos alone on failure,
then the existing /g and /c work well.

    @w = /(\w+)/g;
    @w = /(\w+)/gc;

But if I want to do some lexing then I need /g to enable \G.  As long as
I use scalar context that's fine.

    if (/(\w)+/gc) {
	($foo) = ($1);

but if I want to assign to a list I'm stuck;  that would create a list
context indicating I want multiple matches.

    if (($foo) = /(\w)+/gc) {      # bad

I want to give a list context for assignment to variables and I need \G
to work.  With the context overloading of /g that's impossible.

If there was a /l for lexing that enabled \G without adding the global
matching of /g then I'd be happy and I suspect a lot of other people
would stop making the same mistake and bothering you about it.

    if (($foo) = /(\w)+/lc) {      # bad

Making /gc work so pos wasn't reset on the last, guaranteed to fail,
iteration wouldn't cut it AFAICS.  It would still give me multiple
matches which aren't desired.

    ($foo) = /(\w+)\s*/lc;    # takes one word.
    ($foo) = /(\w+)\s*/gc;    # takes many words returning one.

To sum up, /g means two things (many matches and enable \G), it means
you can't just enable \G.

Thanks for your time.


Thread Previous | Thread Next Perl Programming lists via nntp and http.
Comments to Ask Bjørn Hansen at | Group listing | About