-1

我有一个名为A

package A;
use strict;
use warnings;
use v5.12;

sub import {
    my $caller = caller;
say 'import called from ' . $caller;
    if (not $caller->can('has')) {
        no strict 'refs';
say "--> import has to $caller";
        *{"${caller}::has"} = sub { _attr($caller, @_) };
    }
}

sub _attr {
    my ($class, $name, $default) = @_;
    no strict 'refs';
    *{"${class}::$name"} = sub {
        my ($self, $value) = @_;
        $self->{$name} = $value if $value;
        return $self->{$name} // $default;
    };
}

1;

并有一个子类B

package B;
use strict;
use warnings;
use lib './';
use base 'A';
use v5.12;

#use C;
A->import();

has 'ans' => 42;
say ans();

1;

如果我尝试运行此代码,则会出现语法错误,但如果我对这些进行更改has 'ans' => 42'has('ans' => 42);那么一切都会很好。

或者,如果我创建了类C

package C;
use strict;
use warnings;
use lib '.';
use base 'A';

1;

那么我不需要修改此代码has 'ans'...has(...因为一切正常。

所以,我无法理解为什么会发生这种情况。如何has在子模块中导入子程序?

4

1 回答 1

1

has要从任何其他模块导入,A您只需use A放入该模块即可。

替换这一行:

A->import();

和:

use A;

它会做你想做的事。

手动调用->import不会做您想要的,因为它发生在运行时,并且导入需要在编译时发生,以便在解析使用它的行之前perl知道这是一个子例程名称。是一个编译时命令,因此在该行被解析之前生效。hasusehas

于 2013-01-26T22:39:19.160 回答