perl - 为什么包 A 中的函数在递归调用时不会被导入包 B?

标签 perl recursion package

我正在尝试使用两个包并从一个到另一个调用函数,但是我遇到了这个错误:

未定义的子例程 &module2::method_1_2 在 module2.pm 第 20 行调用。

有没有办法从一个包调用函数到另一个包而不会出现此错误?

提前致谢。

夏比

执行错误:

./test.pl
method_1_1
method_2_1
method_2_2
Undefined subroutine &module2::method_1_2 called at module2.pm line 20.

示例代码(test.pl):
#!/usr/bin/perl

use strict;
use module1;
use module2;

method_1_1();
method_2_2();

模块1.pm
package module1;

use strict;

use module2;

require Exporter;
use vars qw(@ISA @EXPORT);
@ISA     = qw(Exporter);
@EXPORT  = qw( method_1_1 method_1_2 );

sub method_1_1
{
   print "method_1_1\n";
   method_2_1();
}

sub method_1_2
{
   print "method_1_2\n";
}

1;

模块2.pm:
package module2;

use strict;

use module1;

require Exporter;
use vars qw(@ISA @EXPORT);
@ISA     = qw(Exporter);
@EXPORT  = qw( method_2_1 method_2_2 );

sub method_2_1
{
   print "method_2_1\n";
}

sub method_2_2
{
   print "method_2_2\n";
   method_1_2();
}

1;

最佳答案

问题是第一件事module1是到use module2 .这意味着所有 module2module1 时读取并执行仍在编译。

接下来发生的事情是 module2 use module1 .因为module1已找到并放入%INC Perl 不再执行它,只是执行 module1->import获取导出的符号。

但是当然 module1实际上才刚刚开始编译,@module1::EXPORT甚至不存在,更不用说它的两个子例程了。这使得 Exporter什么都不导入module2 ,所以在调用电话时 method_1_2()它对此一无所知。

解决此问题的最简单方法是在编译后(包括所有 use 语句和 BEGIN block )但在运行时之前执行导入。 Perl 的 INIT block非常适合这一点,我们可以通过将模块更改为下面的形式来使代码正常工作。我只展示了module2在这里,调用模式意味着这就是解决此特定问题所需的全部内容,但一般情况下需要对所有协作模块进行等效更改。

package module2;

use strict;
use warnings;

use module1;
INIT { module1->import }

use base 'Exporter';
our @EXPORT  = qw( method_2_1 method_2_2 );

sub method_2_1 {
   print "method_2_1\n";
}

sub method_2_2 {
   print "method_2_2\n";
   method_1_2();
}

1;

关于perl - 为什么包 A 中的函数在递归调用时不会被导入包 B?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11521584/

相关文章:

Java - 我是否必须在包包含的所有类中注释包?

android - Macbook M1 : An error occurred while trying to compute required packages 上有关 Android Studio 的错误

perl - 在@INC 中高级搜索函数

仅适用于某些 child 的 PHP 树依赖列表

c - 递归——数学公式,写程序

c - 返回char数组中数字的递归函数

android - 为什么 Android studio 会遇到大写包名的问题?

regex - Perl 正则表达式匹配文本字符串并提取后面的数字

perl - 如何在 Perl 中格式化时间戳?

bash - 如何将字符串转换为修改后的十六进制表示?