Beefy Boxes and Bandwidth Generously Provided by pair Networks
Welcome to the Monastery
 
PerlMonks  

Re: Invoking a method whose name is computed

by AnomalousMonk (Abbot)
on Oct 02, 2012 at 02:10 UTC ( #996787=note: print w/ replies, xml ) Need Help??


in reply to Invoking a method whose name is computed

Is there a more straightforward version?

I don't know if you will consider it more straightforward, but the  can() universal method can be used here (see The UNIVERSAL Class in perlobj). As the original example is a class method call, argument passing is, well, straightforward. Had it been an object method, the object reference would need to be passed explicitly as the first argument. (Update: See the reply of afoken for the correct way to invoke with class name or object reference.) Also be aware that if the method does not exist,  can() returns undef.

>perl -wMstrict -le "use 5.014; ;; package Foo { sub bar_baz { print 'i am bar_bazing! ', @_; } } ;; my $x = 'baz'; Foo->can(qq{bar_$x})->('Hooray!'); " i am bar_bazing! Hooray!


Comment on Re: Invoking a method whose name is computed
Select or Download Code
Re^2: Invoking a method whose name is computed
by afoken (Prior) on Oct 02, 2012 at 05:43 UTC

    You invoke Foo::bar_baz as function, not as method. For a method call, the object / class name implicitly added by perl is missing, so you have to add it manually:

    Class->can("prefix_$name")->(Class,'first argument'); $object->can("prefix_$name")->($object,'first argument');

    Hardly DRY. I prefer "wasting" a variable for composed method names:

    my $method="prefix_$name"; Class->$method('first argument'); $object->$method('first argument');

    Alexander

    --
    Today I will gladly share my knowledge and experience, for there are no sweeter words than "I told you so". ;-)

      An advantage of the "wasted variable" (I prefer to think it is an "intelligently used variable") is that you can perform a little validation:

      my $object = bless {hi => 'hello'}; for my $suffix ('x', 'y') { my $method = $object->can("prefix_$suffix"); $object->$method() if $method; } sub prefix_x { my ($self) = @_; print "$self->{hi} world\n"; }

      Update: elaborate code to better show intent.

      True laziness is hard work
Re^2: Invoking a method whose name is computed
by tobyink (Abbot) on Oct 02, 2012 at 16:30 UTC

    A pretty good solution, but doesn't work for autoloaded methods unless the developer has been conscientious and overloaded can correctly.

    perl -E'sub Monkey::do{say$_,for@_,do{($monkey=[caller(0)]->[3])=~s{::}{ }and$monkey}}"Monkey say"->Monkey::do'

Log In?
Username:
Password:

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

How do I use this? | Other CB clients
Other Users?
Others studying the Monastery: (13)
As of 2015-07-03 13:50 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    The top three priorities of my open tasks are (in descending order of likelihood to be worked on) ...









    Results (53 votes), past polls