面向对象的 Perl 构造函数语法和命名参数 [英] Object-Oriented Perl constructor syntax and named parameters

查看:23
本文介绍了面向对象的 Perl 构造函数语法和命名参数的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我对 Perl 构造函数中发生的事情有些困惑.我发现这两个例子 perldoc perlbot.

I'm a little confused about what is going on in Perl constructors. I found these two examples perldoc perlbot.

package Foo;

#In Perl, the constructor is just a subroutine called new.
sub new {
  #I don't get what this line does at all, but I always see it. Do I need it?
  my $type = shift;

  #I'm turning the array of inputs into a hash, called parameters.
  my %params = @_;

  #I'm making a new hash called $self to store my instance variables?
  my $self = {};

  #I'm adding two values to the instance variables called "High" and "Low".
  #But I'm not sure how $params{'High'} has any meaning, since it was an
  #array, and I turned it into a hash.
  $self->{'High'} = $params{'High'};
  $self->{'Low'} = $params{'Low'};

  #Even though I read the page on [bless][2], I still don't get what it does.
  bless $self, $type;
}

另一个例子是:

package Bar;

sub new {
  my $type = shift;

  #I still don't see how I can just turn an array into a hash and expect things
  #to work out for me.
  my %params = @_;
  my $self = [];

  #Exactly where did params{'Left'} and params{'Right'} come from?
  $self->[0] = $params{'Left'};
  $self->[1] = $params{'Right'};

  #and again with the bless.
  bless $self, $type;
}

这是使用这些对象的脚本:

And here is the script that uses these objects:

package main;

$a = Foo->new( 'High' => 42, 'Low' => 11 );
print "High=$a->{'High'}
";
print "Low=$a->{'Low'}
";

$b = Bar->new( 'Left' => 78, 'Right' => 40 );
print "Left=$b->[0]
";
print "Right=$b->[1]
";

我已经将我一直遇到的问题/困惑作为注释注入到代码中.

I've injected the questions/confusion that I've been having into the code as comments.

推荐答案

回答您问题的主要内容,因为可以将哈希初始化为 key => 的列表.value 对,您可以将这样的列表发送给函数,然后将 @_ 分配给散列.这是在 Perl 中处理命名参数的标准方法.

To answer the main thrust of your question, since a hash can be initialized as a list of key => value pairs, you can send such a list to a function and then assign @_ to a hash. This is the standard way of doing named parameters in Perl.

例如

sub foo { 
    my %stuff = @_;
    ...
}

foo( beer => 'good', vodka => 'great' );

这将导致子程序 foo 中的 %stuff 具有带有两个键的哈希值,beervodka, 以及相应的值.

This will result in %stuff in subroutine foo having a hash with two keys, beer and vodka, and the corresponding values.

现在,在 OO Perl 中,还有一些额外的问题.每当您使用箭头 (->) 运算符来调用方法时,箭头左侧的任何内容都会被粘贴到 @_ 数组的开头.

Now, in OO Perl, there's some additional wrinkles. Whenever you use the arrow (->) operator to call a method, whatever was on the left side of the arrow is stuck onto the beginning of the @_ array.

所以如果你说 Foo->new( 1, 2, 3 );

然后在您的构造函数中,@_ 将如下所示:( 'Foo', 1, 2, 3 ).

Then inside your constructor, @_ will look like this: ( 'Foo', 1, 2, 3 ).

所以我们使用 shift,它不带参数对 @_ 进行隐式操作,从 @_ 中取出第一项,并且将其分配给 $type.之后,@_ 只剩下我们的名称/值对了,为了方便,我们可以将它直接分配给一个哈希.

So we use shift, which without an argument operates on @_ implicitly, to get that first item out of @_, and assign it to $type. After that, @_ has just our name/value pairs left, and we can assign it directly to a hash for convenience.

然后我们将 $type 值用于 bless.bless 所做的只是获取一个引用(在您的第一个示例中为哈希引用)并说此引用与特定包相关联".阿拉卡扎姆,你有对象.

We then use that $type value for bless. All bless does is take a reference (in your first example a hash ref) and say "this reference is associated with a particular package." Alakazzam, you have an object.

记住 $type 包含字符串 'Foo',它是我们包的名称.如果您bless指定第二个参数,它将使用当前包的名称,这在本例中也适用,但 适用于继承的构造函数.

Remember that $type contains the string 'Foo', which is the name of our package. If you don't specify a second argument to bless, it will use the name of the current package, which will also work in this example but will not work for inherited constructors.

这篇关于面向对象的 Perl 构造函数语法和命名参数的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆