Beefy Boxes and Bandwidth Generously Provided by pair Networks
The stupid question is the question not asked
 
PerlMonks  

How do I reference methods?

( #62737=categorized question: print w/ replies, xml ) Need Help??
Contributed by Faidros on Mar 07, 2001 at 16:50 UTC
Q&A  > object-oriented programming


Description:

With a normal sub I can do this:
$ref = \&MyFunc;
..which will make $ref a reference to the sub MyFunc. But how do I do it if MyFunc is a method in the $self object? I want to make a reference to $self->MyFunc so $self is passed when I call it, but neither
$ref = \&$self->MyFunc;
nor
$ref = \$self->MyFunc;
seems to work. Perl says "Undefined subroutine" for the first, and "not a CODE reference" for the second. So, question is, how do I reference a method so the object is sent when I call the reference, or is there a workaround for the problem?

Answer: How do I reference methods?
contributed by Joost

you can use the UNIVERSAL::can method:

my $object = Ojbect->new; # normal call $object->call(); # get ref my $ref = $object->can('call'); $ref->($object); # use reference..

This will also follow normal inheritance rules.

Note: you probably need to use the object you want to call as the first argument, because normal object methods expect $self to be the first arguments. (that's what $object->call() does anyway)...

Answer: How do I reference methods?
contributed by RocketInABog

Though there are other interesting ways of getting a method reference, there already exists an equivalently straightforward way of doing this.

$ref = \&Class::method; $instance = new Class; $ref->( $instance, @args ); # - calls method of Class for the given i +nstance
Answer: How do I reference methods?
contributed by mirod

You can use closures:

#!/bin/perl -w use strict; # just a simple package package obj; sub new { return bless {content => $_[0]}; } sub print { my $self= shift; print ref($self), ": ", $self->{content}, " - ", @_, "\n"; } # now the main stuff package main; my $p; # that's your method reference { my $o= obj::new( "toto"); # the normal way: create $o->print( "tata"); # print $p=sub { $o->print(@_); }; # create the closure (an anon sub) $p->( "titi"); # use it to print $o= obj::new "foo"; # change the object $p->("tutu"); # print using the new object } my $o= obj::new "bar"; # the $o used with the closure is not # in scope any more $p->("tutu"); # but $p still uses it

This returns:

obj: toto - tata obj: toto - titi obj: foo - tutu obj: foo - tutu

Note that as far as convenience goes calling $o->print or $p->print is pretty similar ;--)

Answer: How do I reference methods?
contributed by LanX

Many complicated ways of calling the reference to a method have been proposed. This one is easier and straightforward.

$obj->$ref2meth(...paras...);
Unfortunately the documentation is lousy, that's why it's fairly unknown! For more details please see OOP: Obj->Coderef for calling Private Methods
Answer: How do I reference methods?
contributed by ariels

See my note on pointers to member functions.

That code lets you say:

use PMF; my $p = PMF->new('print'); $p->$o(123); # Call $o->print(123) $p->$x('a','b'); # Call $x->print('a','b') $p->$z(); # Call $z->print
Answer: How do I reference methods?
contributed by Anonymous Monk

Another stupid way:

use obj; $o = new obj; $ref = sub{$o->method(@_)}; #so if you want to call ref: #&ref('arg1','arg2'[,...]);
Answer: How do I reference methods?
contributed by davorg

All very kludgy, but you could do something like the following. Remember that the first parameter to an object method must be a reference to an object of the right type.

#!/usr/bin/perl -w use strict; package Thing; sub new { bless {}, shift; } sub say { print "@_[1 .. $#_]\n"; } package main; my $thing = Thing->new; $thing->say('Hello', 'World'); my $say = \&Thing::say; $say->($thing, 'Goodbye', 'All');

Please (register and) log in if you wish to add an answer



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.
  • Log In?
    Username:
    Password:

    What's my password?
    Create A New User
    Chatterbox?
    and the web crawler heard nothing...

    How do I use this? | Other CB clients
    Other Users?
    Others wandering the Monastery: (5)
    As of 2015-07-28 01:39 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 (251 votes), past polls