Beefy Boxes and Bandwidth Generously Provided by pair Networks
XP is just a number
 
PerlMonks  

Different way to use while loop

by ChuckP (Novice)
on Jan 09, 2015 at 03:25 UTC ( [id://1112691]=perlquestion: print w/replies, xml ) Need Help??

ChuckP has asked for the wisdom of the Perl Monks concerning the following question:

Greetings,

I just had a co-worker ask what this code did and I didn't know.

while (<FH>) { 1 while s/^FOO/BAR/g; print "$_"; }

It seems to work just like:

while(1) { s/^FOO/BAR/g; print "$_"; }

Any thoughts?

Replies are listed 'Best First'.
Re: Different way to use while loop
by LanX (Saint) on Jan 09, 2015 at 03:44 UTC
    This

      1 while s/^FOO/BAR/g;

    repeats the substitution till it fails¹ ...

    ...which doesn't make much sense because of the ^ anchoring at the start, i.e. it can't substitute more than once.

    This should lead to the same results

    while (<FH>) { s/^FOO/BAR/; print "$_"; }

    The rest (iterating over lines from filehandle with $_) should be obvious, right?

    If not have a look at perlintro

    Cheers Rolf

    PS: Je suis Charlie!

    update
    ¹) it's a postfix equivalent of

    while (s/^FOO/BAR/g) { 1 ; # no op }

      repeats the substitution till it fails ...

      What kind of substitution is it?

      Its a global substitution, so even if it was  s/FOO/BAR/g there would be no need to repeat that, the global substitution took care of it in one pass

        > the global substitution took care of it in one pass

        not in scalar context which is enforced by the boolean context of the while condition.

        see s///g in perlop, perlre , perlretut

        Cheers Rolf

        PS: Je suis Charlie!

        update
        Global matching

        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. You can get or set the position with the pos() function.

        update

        I was wrong the scalar thing is only valid for m//g , s///g just returns the number of all substitutions

        DB<112> $_ = "a a a" => "a a a" DB<113> scalar s/a/x/g => 3

        update

        See this example in perlop for a similar use case

        1 while s/(\d)(\d\d\d)(?!\d)/$1,$2/g;

        But without knowing Foo and Bar we can only speculate.

        Its a global substitution, so even if it was s/FOO/BAR/g there would be no need to repeat that, the global substitution took care of it in one pass
        Not necessarily:
        $ perl -E '$_ = "caattt"; s/at//g; say' catt $ perl -E '$_ = "caattt"; 1 while s/at//g; say' ct
        Without knowing FOO and BAR, we can't say whether new instances of FOO might be created in the string when the substitution is performed.
Re: Different way to use while loop
by Krambambuli (Curate) on Jan 09, 2015 at 09:41 UTC

    The following code should illustrate the difference:

    #!/usr/bin/perl $_ = "Foollll\nFoollll\n"; 1 while s/^Fool/Foo/g; print "1:\n\n$_"; print "\n\n"; $_ = "Foollll\nFoollll\n"; s/^Fool/Foo/g; print "2:\n\n$_";

    Can you see what the output will be...? ;)


    Krambambuli
    ---

      Howdy!

      Thanks for the info and examples! I read perlop and perlre years ago, but don't recall seeing the 1 while example(s).

      Thanks Again!

Re: Different way to use while loop
by soonix (Canon) on Jan 09, 2015 at 09:41 UTC
    1 while condition;
    is a little shorter than
    while(condition){};

    The repetition could make a difference, if BAR sometimes could sometimes contain FOO (what I'd call a recursive substitution, even if in fact it's an iteration ;-)

Re: Different way to use while loop (obfuscation)
by Anonymous Monk on Jan 09, 2015 at 03:32 UTC

    I just had a co-worker ask what this code did and I didn't know. ... It seems to work just like: ... Any thoughts?

    Use more words to explain the program, for example start with <c> $_ contains "foo" , then loop for blah blah and on blah iteration blah happen s...

    Do that for 2/3 of the loops you posted

    Think about what you're saying

    Explain in great detail what happens to the variable at each step, what operator or control structure does

    Say it out loud, write it down, it shouldn't take more than two minutes to write it up ... I'll wait

Log In?
Username:
Password:

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

How do I use this?Last hourOther CB clients
Other Users?
Others having an uproarious good time at the Monastery: (None)
    As of 2024-04-25 01:03 GMT
    Sections?
    Information?
    Find Nodes?
    Leftovers?
      Voting Booth?

      No recent polls found