我想要一些属性(也许这是在这种情况下这是错误的术语)是私有的,也就是说,只有内部用于对象使用 - 不能从外部读取或写入。
例如,考虑一些内部变量,它计算调用任何一组方法的次数。
我应该在哪里以及如何定义这样的变量?
答案 0 :(得分:15)
Moose::Manual::Attributes
显示以下创建私有属性的方法:
has '_genetic_code' => (
is => 'ro',
lazy => 1,
builder => '_build_genetic_code',
init_arg => undef,
);
设置init_arg
表示无法在构造函数中设置此属性。如果您需要更新,请将其设为rw
或添加writer
。
/ I3az /
答案 1 :(得分:10)
您可以尝试这样的事情:
has 'call_counter' => (
is => 'ro',
writer => '_set_call_counter',
);
is => 'ro'
使属性只读。穆斯产生一个吸气剂。您的方法将使用getter来增加值,如下所示:
sub called {
my $self = shift;
$self->_set_call_counter( $self->call_counter + 1 );
...
}
writer => '_set_call_counter'
会生成一个名为_set_call_counter
的setter。 Moose不支持真正的私有属性。从技术上讲,外部代码可以调用_set_call_counter
。但是,按照惯例,应用程序不会调用以下划线开头的方法。
答案 2 :(得分:7)
我想你想要MooseX::Privacy。
perldoc会告诉您所需的一切 - 它会为您的属性添加一个新特征,允许您将它们声明为私有或受保护:
has config => (
is => 'rw',
isa => 'Some::Config',
traits => [qw/Private/],
);
答案 3 :(得分:3)
Alan W. Smith提供了一个带有词法变量的私有类变量,但它由类中的所有对象共享。尝试在示例脚本的末尾添加一个新对象:
my $c1 = CountingObject->new();
printf( "%s\n", $c1->get_count() );
# also shows a count of 10, same as $co
使用MooseX:隐私是一个很好的答案,但如果你不能,你可以从内到外的对象阵营中借用一个技巧:
package CountingObject;
use Moose;
my %cntr;
sub BUILD { my $self = shift; $cntr{$self} = 0 }
sub add_one { my $self = shift; $cntr{$self}++; }
sub get_count { my $self = shift; return $cntr{$self}; }
1;
这样,每个对象的计数器都存储为词法哈希中的条目。因此可以更加简洁地实现上述目标:
package CountingObject;
use Moose;
my %cntr;
sub add_one { $cntr{$_[0]}++ }
sub get_count { return $cntr{$_[0]}||0 }
1;
答案 4 :(得分:2)
我无法找到一种让Moose属性完全隐私的方法。每当我使用has 'name' => (...);
创建一个属性时,它总是会被阅读至少。对于我想要真正私密的项目,我在Moose包中使用标准的“my”变量。有关快速示例,请使用以下模块“CountingObject.pm”。
package CountingObject;
use Moose;
my $cntr = 0;
sub add_one { $cntr++; }
sub get_count { return $cntr; }
1;
使用该模块的脚本无法直接访问$ cntr变量。他们必须使用“add_one”和“get_count”方法,这些方法充当外部世界的接口。例如:
#!/usr/bin/perl
### Call and create
use CountingObject;
my $co = CountingObject->new();
### This works: prints 0
printf( "%s\n", $co->get_count() );
### This works to update $cntr through the method
for (1..10) { $co->add_one(); }
### This works: prints 10
printf( "%s\n", $co->get_count() );
### Direct access won't work. These would fail:
# say $cntr;
# say $co->cntr;
我是Moose的新手,但据我所知,这种方法提供了完全私有的变量。