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

Explanation of commonly used Perl

by tradez (Pilgrim)
on Apr 16, 2002 at 21:34 UTC ( #159635=perlquestion: print w/ replies, xml ) Need Help??
tradez has asked for the wisdom of the Perl Monks concerning the following question:

Fellow monks, I use this alot but I have never been able to understand exactly what was going on it there. The code as you have all used / seen before it
sub foobar { my ($foo, $bar) = @{{@_}}{qw/foo bar/}; #the @{{}}{} logic }
What is going on in there?

Tradez
"Never underestimate the predicability of stupidity"
- Bullet Tooth Tony, Snatch (2001)

Comment on Explanation of commonly used Perl
Download Code
Re: Explanation of commonly used Perl
by swiftone (Curate) on Apr 16, 2002 at 21:49 UTC
    Search for "slices" inside perldata:

    Entire arrays (and slices of arrays and hashes) are denoted by '@', which works much like the word "these" or "those" does in English, in that it indicates multiple values are expected.

    @days # ($days[0], $days[1],... $days[n]) @days[3,4,5] # same as ($days[3],$days[4],$days[5]) @days{'a','c'} # same as ($days{'a'},$days{'c'})
    (end quoting)
    So that given a call like foobar(foo => "a", bar =>"b"), It translates to
    my ($foo, $bar) = @{ {foo => "a", bar => "b"} }{ 'foo','bar'}

    which is essentially the same as ($passed_values{'foo'},$passed_values{'bar'}) It's just unusual because we don't use the @variable{'a','b'} form terribly often.

Re: Explanation of commonly used Perl
by Chmrr (Vicar) on Apr 16, 2002 at 21:56 UTC

    Unroll it, bit by bit:

    @_We'll take the parameters passed to the sub..
    {@_}..and make an anonymous hash out of them.
    {{@_}}{ ... }..now we're going to dereference this hashref..
    @{{@_}}{qw/ ... /}..but take a slice of it when we do so;
    @{{@_}}{qw/foo bar/}Specifically, we'll extract the foo and bar values from the hashref..
    my ($foo, $bar) = @{{@_}}{qw/foo bar/}..and put them into $foo and $bar

    Essentially, the code is equivilent to the following, but avoids the %args variable:

    sub foobar { my %args = @_; my $foo = $args{foo}; my $bar = $args{bar}; }

    perl -pe '"I lo*`+$^X$\"$]!$/"=~m%(.*)%s;$_=$1;y^`+*^e v^#$&V"+@( NO CARRIER'

      In my opinion, your translation is a whole lot easier to read and probably a better idea for maintainable code. The original is pretty obfuscated and would definitely confuse a beginner.

        I would agree. The only "advantage" to doing the hashref / dereference / slice trick is that one avoids the %args hash; frankly, I don't consider that an advantage at all. Most of the time when I pass args to a function as a hash, I simply use the %args hash in the function, instead of pulling specific values out and stuffing them into scalars. I like to think that this makes for better maintainability and scalability.

        But to each their own..

        perl -pe '"I lo*`+$^X$\"$]!$/"=~m%(.*)%s;$_=$1;y^`+*^e v^#$&V"+@( NO CARRIER'

Re: Explanation of commonly used Perl
by mirod (Canon) on Apr 16, 2002 at 21:56 UTC

    Well, first I have never used, nor seen this code, so it is probably not that common.

    It is quite clever though: it lets you call foobar with named parameters passed through a hash: use foobar( bar => 'value of bar', foo => 'this is foo') and $foo will be 'this is foo' and $bar will be 'value of bar'.

    What happens is that %{{@_}} takes @_ and turns it into a hash: the content of @_ ({@_}) is used to create an anonymous hash (%{{@_}}). But what you really want here is only the values, not the keys from this hash, so all (!) you have to do is take a slice of this hash: @{{@_}}{'foo', 'bar'} is the list of values associated to the keys foo and bar in the hash.

    Sweet!

Re: Explanation of commonly used Perl
by particle (Vicar) on Apr 16, 2002 at 22:40 UTC
    I use this alot but I have never been able to understand exactly what was going on it there

    this is called cargo-cult programming. be very careful of this practice. as stated in that link,

    One of our illustrious members once had the habit of crying "cargo cult!" whenever he saw someone cut and paste a code snippet into a program. In particular, he was decrying the habit of cutting and pasting bad code. But even cutting and pasting good code is not necessarily a good thing.

    this code is bad for maintainence, because it's fragile. its not obvious at first glance that the quoted words are assigned to the lvalues, because they're mapped through an obfuscated route.

    better alternatives include the translations provided by swiftone and Chmrr, especially Chmrr's. it's straight forward, direct, and its format allows easy modification.

    although your code provides an interesting use of anonymous data structures and slices, i would never use it in production code.

    ~Particle ;

Log In?
Username:
Password:

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

How do I use this? | Other CB clients
Other Users?
Others musing on the Monastery: (13)
As of 2014-10-23 21:17 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    For retirement, I am banking on:










    Results (129 votes), past polls