Beefy Boxes and Bandwidth Generously Provided by pair Networks
Perl: the Markov chain saw
 
PerlMonks  

What is this doing, and why is this a good method of doing it?

by japhy (Canon)
on Jul 24, 2005 at 21:34 UTC ( [id://477620]=obfuscated: print w/replies, xml ) Need Help??

use strict; my @x = somefunction(); for (@x) { *{; no strict 'refs'; \*$_} = sub { # ... }; }

Jeff japhy Pinyan, P.L., P.M., P.O.D, X.S.: Perl, regex, and perl hacker
How can we ever be the sold short or the cheated, we who for every service have long ago been overpaid? ~~ Meister Eckhart

Replies are listed 'Best First'.
Re: What is this doing, and why is this a good method of doing it?
by Zaxo (Archbishop) on Jul 25, 2005 at 02:04 UTC

    It is producing a named subroutine for each name in @x. Even if somefunction() returns names which would be illegal for a sub, a function of the name will be provided.

    use strict; use warnings; sub somefunction { qw/foo bar 123/ } my @x = somefunction(); for (@x) { my $foo = "${_}_func"; *{;no strict 'refs'; \*$_} = sub { $foo }; } print &123(),$/; # omitting the & sigil gives syntax error __END__ 123_func

    The tight scope of no strict 'refs'; is remarkable. I've never seen it done that way. I think it is the primary advantage of doing this: stricture in in force in the sub definition. The construction seems to be equivalent to,

    *{ +do { no strict 'refs'; \*$_ } } = sub { # . . . };

    After Compline,
    Zaxo

      Indeed. The function is defined with whatever level of strictures were in effect for the preceding code. Obviously, the code could be written in nicer ways, but the idea is to make sure that (specifically) no symbolic references are used in the code reference.

      Jeff japhy Pinyan, P.L., P.M., P.O.D, X.S.: Perl, regex, and perl hacker
      How can we ever be the sold short or the cheated, we who for every service have long ago been overpaid? ~~ Meister Eckhart
Re: What is this doing, and why is this a good method of doing it?
by IOrdy (Friar) on Jul 25, 2005 at 02:05 UTC
    I'll bite, rather than switching strict refs off then on again is it a good method? Is there a side effect of switching I dont see?

    for (@x) { no strict 'refs'; *$_ = sub { use strict 'refs'; # ... }; }
    Also why is the semicolon required before the no strict 'refs'?

      Because at compile-time, when Perl has parsed the no strict 'refs' part, it realizes it was inside a *{...} construct, the inside of which can be a block or an expression. Since it expects it to have been an expression, the use of no raises a compile-time error. To force Perl to realize the interior is a block, the ; is added to the beginning.

      Jeff japhy Pinyan, P.L., P.M., P.O.D, X.S.: Perl, regex, and perl hacker
      How can we ever be the sold short or the cheated, we who for every service have long ago been overpaid? ~~ Meister Eckhart
      The difference is that here the defined sub has use strict 'refs' in effect, while in Japhy's original code, the defined sub has ref strictness in effect if, and only if, ref strictness is in effect just before the for loop.
Re: What is this doing, and why is this a good method of doing it?
by Tanktalus (Canon) on Jul 25, 2005 at 02:00 UTC
      Yes. Now that you know what it does, do you know why I'm suggesting it be done this way? (Less obfuscated, of course.)

      Jeff japhy Pinyan, P.L., P.M., P.O.D, X.S.: Perl, regex, and perl hacker
      How can we ever be the sold short or the cheated, we who for every service have long ago been overpaid? ~~ Meister Eckhart
Re: What is this doing, and why is this a good method of doing it?
by simonm (Vicar) on Jul 24, 2005 at 22:18 UTC
    That's certainly an unusual scope in which to apply a lexical pragma -- nice work.

    It's kinda surprising that it works like that; I wonder how reliably it would work on older versions, or in flavors of P6...

Re: What is this doing, and why is this a good method of doing it?
by ihb (Deacon) on Jul 26, 2005 at 19:29 UTC

    I think I prefer

    use Symbol qw/ qualify_to_ref /; *{ qualify_to_ref($name) } = sub { ... };

    ihb

    See perltoc if you don't know which perldoc to read!

Re: What is this doing, and why is this a good method of doing it?
by nothingmuch (Priest) on Jul 28, 2005 at 10:01 UTC
    Does this capture the essence?
    my @x = somefunction(); my @xs = map { { name => $_, sub => sub { ... }, } } @x; for (@xs) { no strict 'refs'; *{ $_->{name} } = $_->{sub}; }
    -nuffin
    zz zZ Z Z #!perl

Log In?
Username:
Password:

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

How do I use this?Last hourOther CB clients
Other Users?
Others taking refuge in the Monastery: (6)
As of 2024-03-19 03:38 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found