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

Perl bug ?

by vsespb (Chaplain)
on Feb 06, 2013 at 11:40 UTC ( [id://1017390]=perlquestion: print w/replies, xml ) Need Help??

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

#!/usr/bin/perl use strict; use warnings; my $errors = undef; sub ok { my( $test, $name ) = @_; print "[[[$test]]] [[[$name]]]\n"; }; ok( ($errors && ($errors->[0] =~ /Journal file not found/i)), "some te +xt 1 $errors->[0]" ); ok( ($errors && ($errors->[0] =~ /Journal file not found/i)), "some te +xt 2 $errors->[0]" );
prints the following:
Use of uninitialized value in concatenation (.) or string at poc.pl li +ne 14. [[[ARRAY(0x137cd48)]]] [[[some text 1 ]]] Use of uninitialized value in pattern match (m//) at poc.pl line 15. Use of uninitialized value in concatenation (.) or string at poc.pl li +ne 15. Use of uninitialized value $name in concatenation (.) or string at poc +.pl line 11. [[[some text 2 ]]] [[[]]]
and by the way this code (with modified 'some text' strings)
#!/usr/bin/perl use strict; use warnings; my $errors = undef; sub ok { my( $test, $name ) = @_; print "[[[$test]]] [[[$name]]]\n"; }; ok( ($errors && ($errors->[0] =~ /Journal file not found/i)), "some te +xt 1" ); ok( ($errors && ($errors->[0] =~ /Journal file not found/i)), "some te +xt 2" );
prints correct result:
Use of uninitialized value $test in concatenation (.) or string at poc +.pl line 11. [[[]]] [[[some text 1]]] Use of uninitialized value $test in concatenation (.) or string at poc +.pl line 11. [[[]]] [[[some text 2]]]
perl 5.10.1 under Linux

Replies are listed 'Best First'.
Re: Perl bug ?
by choroba (Cardinal) on Feb 06, 2013 at 11:54 UTC
    You have stumbled upon autovivification. After expanding $error->[0] in the double quoted string, Perl creates the referenced array for you, so $error is now [].
    لսႽ† ᥲᥒ⚪⟊Ⴙᘓᖇ Ꮅᘓᖇ⎱ Ⴙᥲ𝇋ƙᘓᖇ
      You are right.
      #!/usr/bin/perl my $errors = undef; $errors->[0]; print $errors
      prints ARRAY(0x15bad48). I didn't realize that autovivification happens even on read-only access =)
      But why ARRAY ref passed to subroutine ? Argument is
      ($errors && ($errors->[0] =~ /Journal file not found/i))
      so it should be evaluated to false ?
        the first call of ok():
        the first argument is $errors && ($errors->[0] =~ /.../i) which results in $errors being passed as the first argument. before it is passed, array element 0 gets autovivivied though by usage in the second argument.

        the second call:
        $errors is now true, so the matching is executed and its result would the empty string ("false"). but since the matching is executed in list context, the result is an empty list, so what you wrote as a second argument becomes now the first argument.
        Update: Disregard. See rather Re^5: Perl bug ?.

        The order in which arguments to subroutines are processed is not guaranteed:

        sub test { say for @_ } test($x=0, $x=$x+1, $x++, ++$x);
        Returns:
        3 3 1 3
        لսႽ† ᥲᥒ⚪⟊Ⴙᘓᖇ Ꮅᘓᖇ⎱ Ⴙᥲ𝇋ƙᘓᖇ
Re: Perl bug ?
by Corion (Patriarch) on Feb 06, 2013 at 12:38 UTC
      or here https://rt.perl.org/rt3/Ticket/Display.html?id=116665
Re: Perl bug ?
by salva (Canon) on Feb 06, 2013 at 11:57 UTC
    The first warning is generated in "some text 1 $errors->[0]" because $errors->[0] is undefined.

    That expression also has the side effect of autovivifying $errors and that causes the $errors check on the test on the following line to succeed.

Log In?
Username:
Password:

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

How do I use this?Last hourOther CB clients
Other Users?
Others avoiding work at the Monastery: (6)
As of 2024-04-23 12:10 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found