在这个早期的Stackoverflow问题中,特别是brian d foy的"脚本如何成为一个模块"我已经阅读了如何设置代码,以便它可以作为脚本或模块运行,使用这种技术:
package SomeModule;
__PACKAGE__->run(@ARGV) unless caller();
sub run {
# Do stuff here if you are running the file as
# a script rather than a module.
}
Run Code Online (Sandbox Code Playgroud)
__PACKAGE__
这个设置的目的是什么?为什么不这样做呢?
run(@ARGV) unless caller();
Run Code Online (Sandbox Code Playgroud)
Cha*_*ens 14
如果你说,__PACKAGE__->run(@ARGV)
那么run
可以在你继承的类中定义,或者允许类从这个类继承.如果你只是说run(@ARGV)
你错过了班级信息.这只在您进行OO样式编程时才有意义.
将以下内容放在一个名为的文件中Foo.pm
,然后说出来perl Foo.pm 1 2 3
package Foo;
use strict;
use warnings;
__PACKAGE__->main(@ARGV) unless caller;
sub main {
my $class = shift;
my $obj = $class->new(@ARGV);
print $obj->to_string, "\n";
}
sub new {
my $class = shift;
return bless [@_], $class;
}
sub to_string {
my $self = shift;
return "args: " . join ", ", map { "[$_]" } @$self;
}
1;
Run Code Online (Sandbox Code Playgroud)
现在把以下内容放进去Bar.pm
说perl Bar.pm a b c
.
package Bar;
use strict;
use warnings;
use base 'Foo';
__PACKAGE__->main(@ARGV) unless caller;
sub to_string {
my $self = shift;
return "args: " . join ", ", map { "<$_>" } @$self;
}
1;
Run Code Online (Sandbox Code Playgroud)
现在让我们看看如果你不在__PACKAGE__
这种环境中使用会发生什么.使代码的第一部分Foo.pm
看起来像这样:
main(@ARGV) unless caller;
sub main {
my $obj = Foo->new(@ARGV);
print $obj->to_string, "\n";
}
Run Code Online (Sandbox Code Playgroud)
现在跑perl Foo.pm 1 2 3
.一切都应该看起来正确.现在尝试跑步perl Bar.pm a b c
.我们仍然得到输出,但它不是我们期望的输出.如果我们__PACKAGE__
从中移除会发生什么Bar.pm
?好吧,我们得到并且错误:Undefined subroutine &Bar::main called at Bar.pm line 8.
这是因为main
模块中没有函数,我们没有用类调用它,因此它Foo
不再在包中查找它.