Beefy Boxes and Bandwidth Generously Provided by pair Networks
Do you know where your variables are?
 
PerlMonks  

What does 'global' (/g) do in a regexp in this particular case?

by DreamT (Pilgrim)
on Apr 09, 2013 at 13:27 UTC ( #1027734=perlquestion: print w/ replies, xml ) Need Help??
DreamT has asked for the wisdom of the Perl Monks concerning the following question:

Dear Monks, The code belongs matches some properties and prints them out:
#!/usr/bin/perl my @AllColumns; push @AllColumns, "Property1"; push @AllColumns, "Property2"; print "Lap 1:\n"; foreach my $Column (@AllColumns) { print "$Column? : "; if ((($Column =~ m/Property/gs))) { print $Column."\n"; } } print "\n\nLap 2:\n"; foreach my $Column (@AllColumns) { print "$Column? : "; if ((($Column =~ m/Property/gs))) { print $Column."\n"; } } 1;

My desired result is that both columns should be printed both times. However, the "g" in the regexp doesn't give me the desired result. Removing it does. Why? Or more specific, how should i use the "g" option?

Comment on What does 'global' (/g) do in a regexp in this particular case?
Download Code
Re: What does 'global' (/g) do in a regexp in this particular case?
by hdb (Prior) on Apr 09, 2013 at 13:37 UTC

    From perlretut:

    "The modifier //g stands for global matching and allows the matching operator to match within a string as many times as possible. In scalar context, successive invocations against a string will have //g jump from match to match, keeping track of position in the string as it goes along. "

    If both your matching operators have /g, they become part of one operation, which can consume "Property" only once.

Re: What does 'global' (/g) do in a regexp in this particular case?
by LanX (Canon) on Apr 09, 2013 at 13:37 UTC
    /g in scalar context iterates over all matches and keeps track of the position, see also pos

    Without /g the match restarts from the beginning, i.e. the string is stateless.

    DB<116> $a="a a" => "a a" DB<117> scalar ($a =~ /a/g) => 1 DB<118> scalar ($a =~ /a/g) => 1 DB<119> scalar ($a =~ /a/g) => "" # exhausted DB<120> $a="a a" => "a a" DB<121> scalar ($a =~ /a/) => 1 DB<122> scalar ($a =~ /a/) => 1 DB<123> scalar ($a =~ /a/) => 1 # ... till infinity

    Cheers Rolf

    ( addicted to the Perl Programming Language)

Re: What does 'global' (/g) do in a regexp in this particular case?
by choroba (Abbot) on Apr 09, 2013 at 13:41 UTC
    As already explained, the /g remembers the position where the last match succeded in $Column. As a workaround, you can use double quotes to make the strings "not the same string":
    if (((("$Column" =~ m/Property/gs))))
    لսႽ ᥲᥒ⚪⟊Ⴙᘓᖇ Ꮅᘓᖇ⎱ Ⴙᥲ𝇋ƙᘓᖇ
      > As a workaround

      ehm, ok! But what for???

      Can't see any benefit of using /g here.

      Cheers Rolf

      ( addicted to the Perl Programming Language)

      Update

      OK at least in a loop pos works on literals...

      DB<139> print scalar "a a" =~ /a/g for 1..10 1111111 # third iteration is undef than restart from beginning DB<140> print scalar "a a" =~ /a/ for 1..10 1111111111 # infinite restart
      $Column is already a different string, DreamT has tripped /g in list context bug -- interpolation breaks aliasing/ causes copying -- jumps out of the bug
        Where is the list context?
        perl -E '$x = "12345"; $a = $x =~ /4/g; $b = $x =~ /1/g; say "$a,$b.\n +"'
        لսႽ ᥲᥒ⚪⟊Ⴙᘓᖇ Ꮅᘓᖇ⎱ Ⴙᥲ𝇋ƙᘓᖇ
Re: What does 'global' (/g) do in a regexp in this particular case? (pos bug)
by Anonymous Monk on Apr 09, 2013 at 13:43 UTC

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://1027734]
Approved by marto
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others about the Monastery: (3)
As of 2014-09-17 23:51 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    How do you remember the number of days in each month?











    Results (100 votes), past polls