【问题标题】:OOP Perl passing @_ to second methodOOP Perl 将 @_ 传递给第二种方法
【发布时间】:2012-07-01 17:14:51
【问题描述】:
#! /usr/bin/perl

# this is the object tester

{package Hate;
sub status {
my $class = shift;
print "-- $_[0] $_[1] $_[2]\n";
print "$class exists and ", $class->stats($_[0]), "and ", $class->type($_[1]), "and ",     $class->location($_[2]);
}
}

{package Grudge;
@ISA = "Hate";
sub stats{"$_[0]\n"}
sub type{"$_[0]\n"}
sub location{"$_[0]\n"}
}

Hate::status("Grudge", @ARGV);

我跑了./program 一二三

这个输出是我所期望的 怨恨存在且一 和两个 和三个

这就是我得到的 怨恨存在和怨恨 和怨恨 和怨恨

但是当我使用这个脚本时

#! /usr/bin/perl

# this is the object tester

{package Hate;
sub status {
my $class = shift;
print "-- $_[0] $_[1] $_[2]\n";
print "$class exists and ", $class->stats($_[0]), "and ", $class->type($_[1]), "and ",     $class->location($_[2]);
}
}

{package Grudge;
@ISA = "Hate";
sub stats{"$_[1]\n"}
sub type{"$_[1]\n"}
sub location{"$_[1]\n"}
}

Hate::status("Grudge", @ARGV);

这行得通。

【问题讨论】:

  • 您是否讨厌或怨恨句子中缩进代码和大写?
  • 我真的不是想听起来很冷嘲热讽,但你为什么指望one two three?也许如果您解释为什么这是您的期望,我们可能会理解脱节是什么。 @ARGV 中还有什么内容?

标签: perl oop inheritance object


【解决方案1】:

在您的第一个示例中,$class->stats($_[0]) 被称为 方法,并作为第一个参数传递一个对象,需要像在 Hate::status 中所做的那样将其移开。这就是$_[1] 起作用的原因:因为该方法的第一个参数实际上是@_ 中的第二项(在$self 之后)。

如果您在函数开头将参数从@_ 中解压缩出来,事情就会变得更加清晰和易于管理,例如

{
    package Hate;
    sub status {
        my ($class, $stats, $type, $location) = @_;
        print "-- $stats $type $location\n";
        print "$class exists and ", $class->stats($stats), ...;
    }
}

{
    package Grudge;
    our @ISA = qw(Hate);
    sub stats { my ($self, $stats) = @_; $stats; }
    sub type { my ($self, $type) = @_; $type; }
    sub location { my ($self, $location) = @_; $location; }
}

Hate::status('Grudge', @ARGV);

附带说明一下,您对对象的使用并不典型 - 如果您提供更多代码,我们或许能够提供更惯用的 Perl 解决方案。例如,您的所有对象都没有构造函数,而目前这三个 Grudge 方法似乎在做同样的事情。也不清楚为什么GrudgeHate 的子类(如@ISA 所示)。

如果您真的不希望 Grudge 将其自己的名称作为参数传递,您可以通过 &{$class . '::stats'}() 将其方法作为函数调用,但您必须禁用 strict subs。通常最好像现在这样调用方法。

【讨论】:

  • 我通常通过执行my $method = $class->can('stats') 来绕过方法调用,然后当您调用$method->(@args) 时,它不会通过自引用。更清洁和strict-安全。 ;-)
  • @JoelBerger:是的,但即便如此,你为什么要这样做?
  • 好吧,说实话,我不会避免方法调用,我需要引用方法,我用$method->($instance, @args) 调用它们,但用法并没有什么不同。为什么@rjh 这样做我不知道。
猜你喜欢
  • 1970-01-01
  • 2015-09-24
  • 1970-01-01
  • 2011-06-30
  • 1970-01-01
  • 1970-01-01
  • 2013-12-18
  • 1970-01-01
  • 2010-11-07
相关资源
最近更新 更多