Beefy Boxes and Bandwidth Generously Provided by pair Networks
P is for Practical
 
PerlMonks  

Re: Perl oddities (s/// doesn't DWIM in map)

by grinder (Bishop)
on Mar 01, 2005 at 13:55 UTC ( [id://435426]=note: print w/replies, xml ) Need Help??


in reply to Perl oddities

I still find myself being tripped up from time to time by the following, even though I should know better:

my @w= qw/ per coercer berserker / ; print "$_\n" for map { s/er/aler/g } @w;

The above produces the output "1 2 3". To make it DWIM, one must say:

my @w = qw/ per coercer berserker / ; print "$_\n" for map { s/er/aler/g; $_ } @w;

I've always found that odd. (Yes, I know why it works that way).

- another intruder with the mooring in the heart of the Perl

Replies are listed 'Best First'.
Re^2: Perl oddities (s/// doesn't DWIM in map)
by TimToady (Parson) on Mar 01, 2005 at 20:12 UTC
    This can be solved much more generically in Perl 6 with mutator methods and topics:
    print "$_\n" for map { .=subst(/er/, 'aler', :global) } @w;
    But what you're really asking for is something other than map here, I think...
Re^2: Perl oddities (s/// doesn't DWIM in map)
by Joost (Canon) on Mar 01, 2005 at 14:06 UTC

      True. I'd like to see a switch:

      my $modified = s/$pattern/$change_to/gr;

      Where /r stands for 'replaced', or somesuch.

        Would that be equivalent to
        (my $modified = $_) =~ s/$pattern/$change_to/g;
        or
        s/$pattern/$change_to/g; my $modified = $_;
        ?

        Caution: Contents may have been coded under pressure.
Re^2: Perl oddities (s/// doesn't DWIM in map)
by Roy Johnson (Monsignor) on Mar 01, 2005 at 20:18 UTC
    A related oddity is that map can modify its input, in addition to generating output. That leads to the pitfall of
    my @new = map { s/foo/bar/; $_ } @old; # @old is modified along with @new! # should be my @new = map { s/foo/bar/; $_ } map {$_} @old;
    If map couldn't modify its input, the whole "map in a void context" debate might never have happened. for would be used for modifying input, map would be used for generating new output. Of course, it's a tradeoff, giving up some liberty for safety.

    Caution: Contents may have been coded under pressure.
      my @new = map { local $_ = $_; s/foo/bar/; $_ } @old; also avoids the problem. Probably faster than using two maps, too. Still ugly, unfortunately.

      I write that as

      s/foo/bar/ for my @new = @old;

      Makeshifts last the longest.

Re^2: Perl oddities (s/// doesn't DWIM in map)
by Roy Johnson (Monsignor) on Mar 01, 2005 at 18:03 UTC
    I understand that you were just giving an example, but it looks like gratuitous chaining to me. Why not just
    for (@w) { s/er/aler/g; print "$_\n"; }
    You might also be interested in Algorithm::Loops 'filter'.

    Caution: Contents may have been coded under pressure.
      Because that might be part of a much larger chain.

      Additionally, what's gratuitous in one set of eyes is natural in another's. For example, I find Java to be a gratuitous (mis)use of classes, but others, like Smalltalkers, find it to be gratuitously procedural. :-)

      Being right, does not endow the right to be rude; politeness costs nothing.
      Being unknowing, is not the same as being stupid.
      Expressing a contrary opinion, whether to the individual or the group, is more often a sign of deeper thought than of cantankerous belligerence.
      Do not mistake your goals as the only goals; your opinion as the only opinion; your confidence as correctness. Saying you know better is not the same as explaining you know better.

Log In?
Username:
Password:

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

How do I use this?Last hourOther CB clients
Other Users?
Others chanting in the Monastery: (1)
As of 2024-04-16 18:31 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found