如何确定Perl函数在运行时是否存在?

dfty9e19  于 2023-01-21  发布在  Perl
关注(0)|答案(4)|浏览(208)

我正在用Perl开发一个测试框架。作为测试的一部分,我可能需要为任何给定的测试添加前置条件或后置条件检查,但不一定要为所有的测试添加前置条件或后置条件检查。到目前为止,我所得到的结果如下:

eval "&verify_precondition_TEST$n";
print $@ if $@;

不幸的是,如果函数不存在,则会输出“未定义的子例程&verify_precondition_TEST1在...处调用”。
在尝试调用函数之前,如何提前确定该函数是否存在?

bis0qfac

bis0qfac1#

Package::Name->can('function')

*Package::Name::function{CODE}

# or no strict; *{ "Package::Name::$function" }{CODE}

或者只是接受这个异常,如果你在eval中调用这个函数并且$@被置位,那么你就不能调用这个函数。
最后,听起来您可能需要Test::Class,而不是自己编写。
Edit:defined &function_name(或no strict; defined &{ $function_name }的变体),正如在其他答案中提到的,看起来是最好的方法。UNIVERSAL::can最适合于你要作为方法调用的东西(从风格上来说),而且既然Perl给了你做你想做的事情的语法,为什么还要费心去摆弄符号表呢?
学习++:)

nkcskrwz

nkcskrwz2#

sub function_exists {    
    no strict 'refs';
    my $funcname = shift;
    return \&{$funcname} if defined &{$funcname};
    return;
}

if (my $subref = function_exists("verify_precondition_TEST$n") {
    ...
}
sshcrbum

sshcrbum3#

定义为:

if (eval "defined(&verify_precondition_TEST$n)") {
    eval "&verify_precondition_TEST$n";
    print $@ if $@;
}
else {
    print "verify_precondition_TEST$n does not exist\n";
}

**编辑:**嗯,我只想到了问题中的eval,但Leon Timmermans提出了一些象征性的引用,你能做到吗

if (defined(&{"verify_precondition_TEST$n"}) {
    &{"verify_precondition_TEST$n"};
    print $@ if $@;
}
else {
    print "verify_precondition_TEST$n does not exist\n";
}

即使是严格的

vybvopom

vybvopom4#

我曾经使用过Leon的方法,但是当我有多个包时,它失败了。我认为它与名称空间之间的作用域传播有关。这是我想出的解决方案。

my %symbols = ();
my $package = __PACKAGE__; # bring it in at run-time
{
    no strict;
    %symbols = %{$package . "::"}; #S ee Symbol Tables on perlmod
}
print "$funcname not defined\n" if (!defined($symbols{$funcname});

参考文献:
perlmod页面上的PACKAGE参考。
Packages/PACKAGE澳大利亚Perl培训参考。

相关问题