Beefy Boxes and Bandwidth Generously Provided by pair Networks Bob
Keep It Simple, Stupid
 
PerlMonks  

map BLOCK evaluation context

by vsespb (Hermit)
on Mar 08, 2013 at 13:52 UTC ( #1022425=perlquestion: print w/ replies, xml ) Need Help??
vsespb has asked for the wisdom of the Perl Monks concerning the following question:

According to perldoc http://perldoc.perl.org/functions/map.html

map should evaluate BLOCK in list context

Evaluates BLOCK or EXPR in list context
but I am wondering why in my example, sometimes it's LIST context, sometimes SCALAR.
print "A:"; print map { /(\S+)/g or die } qq{ab cd}; # prints "A:1" so evaluated i +n scalar context print "\n"; print "B:"; print map { /(\S+)/g } qq{ab cd}; # prints "B:abcd", means evaluated +in list context print "\n"; print "C:"; for (qq{ab cd}) { print /(\S+)/g or die; # prints "C:abcd", list context again } print "\n";

Comment on map BLOCK evaluation context
Select or Download Code
Reaped: Re: map BLOCK evaluation context
by NodeReaper (Curate) on Mar 08, 2013 at 14:19 UTC
Re: map BLOCK evaluation context
by tobyink (Abbot) on Mar 08, 2013 at 14:20 UTC

    Nothing to do with map; it has more to do with precedence. The or operator always returns a scalar.

    Consider:

    print "D:"; for (qq{ab cd}) { print(/(\S+)/g or die); } print "\n";
    package Cow { use Moo; has name => (is => 'lazy', default => sub { 'Mooington' }) } say Cow->new->name
      Yes, but why in "A" example "or" enforces scalar, and in "C" it does not? Also: "or" does not always return a scalar.

        or can supply list contexts to its arguments, but it always returns a scalar... or at least, I've never seen it return a list.

        use Data::Dumper; my @A = qw(1 2 3); my @B = qw(A B C D); print Dumper(@A or @B);

        In example C, or does return a scalar. You just don't do anything with the scalar. print @list or die is not parsed as print(@list or die); it's parsed as print(@list) or die. Therefore, print only sees the list; it doesn't see the result of the or operator.

        Update: meh... the right hand side of or can result in or returning a list:

        use Data::Dumper; my @A = qw(); my @B = qw(A B C D); print Dumper(@A or @B);

        The left hand side cannot.

        package Cow { use Moo; has name => (is => 'lazy', default => sub { 'Mooington' }) } say Cow->new->name
        Aha, you're right. The thing was that
        print "C:"; for (qq{ab cd}) { print /(\S+)/g or die; # prints "C:abcd", list context again } print "\n";
        was evaluated just like
        print "C:"; for (qq{ab cd}) { print(/(\S+)/g) or die; } print "\n";
        It can be fixed like this:
        print "D:"; for (qq{ab cd}) { print /(\S+)/g || die; } print "\n";
        However seems "or" not always enforces scalar context:
        my @a = (1,2,3); print "X:"; print (0 || @a); print "\n"; print "Y:"; print (@a || 0); print "\n";
        prints
        X:123 Y:3

      The or operator always returns a scalar.

      No, only the LHS operand is evaluated in scalar context. The RHS inherits.

      >perl -E"@a=qw( a b c ); say( 0 or @a );" abc
Re: map BLOCK evaluation context
by grondilu (Pilgrim) on Mar 08, 2013 at 14:21 UTC

    Isn't it simply because invoking the boolean OR forces the scalar evaluation of /(\S+)/g ?

    Update: tobyink was quicker than me on this.

Log In?
Username:
Password:

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

How do I use this? | Other CB clients
Other Users?
Others imbibing at the Monastery: (6)
As of 2014-04-18 23:49 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    April first is:







    Results (473 votes), past polls