Home > OS >  Perl dynamic / symbolic function reference
Perl dynamic / symbolic function reference

Time:05-09

Given a package name $package and a function name from within that package $function, I can create a reference to that function:

my $ref = eval( "\\&${package}::${function}" );

As a complete example:

#!/usr/bin/perl -w

use strict;

package foo;

sub func()
{
    print "foo::func\n";
}

package main;

my $package = "foo";
my $function = "func";

my $ref = eval( "\\&${package}::$function" );
$ref->();

I do not particularly like that eval() in there and wonder if the same result could be achieved without eval()?

CodePudding user response:

All you need is this:

my $ref = \&{ "${package}::$name" };

or

my $ref = \&{ $package . "::" . $name };

Using an expression producing the name of a variable where a variable name is expected is called a symbolic reference. These are usually forbidden by use strict; (specifically use strict qw( refs );), but \& is exempt.

CodePudding user response:

Using strings to refer to subroutines is seldom the right way. If you are doing it this way, you are most likely doing something wrong. You can use a code reference to store a reference to a function, in a scalar or hash. The hash allows you to correctly look up code references via string inputs.

use strict;
use warnings;

package foo;
sub func() {
    print "inside foo::func (@_)\n";
}

package main;

# use a direct reference, in a scalar variable
my $ref = \&foo::func;
$ref->(1,2,3);

# ...or in a hash
my $pack = "foo";
my $func = "func";
my %table = ( foo => { func => \&foo::func } );
$table{$pack}{$func}->(qw(a b c));

Output:

inside foo::func (1 2 3)
inside foo::func (a b c)
  • Related