Interesting! I'm going to have to play with some of the dusty corners of regexes. Anyway, while trying to figure it out, I stumbled across this bit in perldoc perlre under the heading "Assertions":
The "\G" assertion can be used to chain global matches (using "m//g"), as described in "Regexp Quote-Like Operators" in perlop. It is also useful when writing "lex"-like scanners, when you have several patterns that you want to match against consequent substrings of your string, see the previous reference. The actual location where "\G" will match can also be influenced by using "pos()" as an lvalue: see "pos" in perlfunc. Note that the rule for zero-length matches is modified somewhat, in that contents to the left of "\G" is not counted when determining the length of the match. Thus the following will not match forever:It will print 'A' and then terminate, as it considers the match to be zero-width, and thus will not match at the same position twice in a row.$str = 'ABC'; pos($str) = 1; while (/.\G/g) { print $&; }
I don't really grok exactly what and why /G and m//g work that way, so I'll have to monkey around with it to get a feel for things. But I'm thinking that that bit of documentation holds the key to your problem.
As for the second part of your question, think of m//g in list context as an iterator where pos() is the (user accessible) interface to the iterator. Before you do a match with m//g, pos is undefined, as there is no active iterator for the string. As you consume each match, the iterator is updated so it can start at the next location. Once you've consumed all the matches, the iterator ends and pos() goes back to being undefined. Since you're executing it in a list context, it's doing *all* the iterations at once, and when you get to your next line of code, the iterator is already exhausted.
...roboticus
When your only tool is a hammer regex, all problems look like your thumb HTML.
Post Script: That's a rather fine first posting to the site.
In reply to Re: [Perl 5.14, regex]: Problems with /g, \G and pos()
by roboticus
in thread [Perl 5.14, regex]: Problems with /g, \G and pos()
by Darkwing
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |