为什么Perl的SUPER调用不使用箭头方法?

Geo*_*Geo 13 oop perl

我注意到当你调用超类的方法时,你需要做这样的事情:

my $self = $class->SUPER::new();
Run Code Online (Sandbox Code Playgroud)

为什么不是这样的:

my $self = $class->SUPER->new();
Run Code Online (Sandbox Code Playgroud)

der*_*ert 14

我怀疑因为$class->SUPER->new()通常会一样$class->SUPER()->new().但是没有一个$class->SUPER()功能,并且不清楚会返回什么.

另一方面,$class->Foo::Bar一直是通过全名直接调用方法的有效方法,因此制作一个特殊的类似于包的东西 - SUPER更适合.(我怀疑你实际上可以实现SUPER一个包,也许它在历史上是,我不知道)

PS:看一下mro包装,然后$self->next::method.另外,如果您要在Perl中进行严肃的OO工作,请查看Moose.

  • 在我使用Moose之前,我想了解背后的东西. (9认同)
  • 看看_Mose的温和介绍_http://www.catalyzed.org/2009/06/a-gentle-introduction-to-moose.html (3认同)
  • @Geo,你只想*你想知道更多.我可以诚实地告诉你,你最好不要知道,直到你遇到它. (2认同)

yst*_*sth 13

方法调用有许多形式:

调用方法,可能继承:

->method()
Run Code Online (Sandbox Code Playgroud)

显式调用sub Package ::方法,无论是否在继承树中:

->Package::method()
Run Code Online (Sandbox Code Playgroud)

显式调用引用的子,无论是否在继承树中:

->$coderef()
Run Code Online (Sandbox Code Playgroud)

__PACKAGE__->method()如果没有子方法,则调用将被调用的方法__PACKAGE__(NB左侧的类或对象->无关紧要):

->SUPER::method()
Run Code Online (Sandbox Code Playgroud)

以上任何一种,取决于以下内容$method:

->$method()
Run Code Online (Sandbox Code Playgroud)

(法律甚至在use strict;.)

虽然第一种形式是最常见的,但值得了解其他形式及其运作方式.


bri*_*foy 13

简而言之,SUPER不是一种方法.这是一个虚拟包.它在"方法调用"部分的perlobj中有记录.

但请注意,SUPER基于当前包,而不是您使用它的实例的包.


Joe*_*Joe 7

添加derobert所说的:

你在'SUPER'命名空间中调用'new',但是传递对象(或字符串)'$ class'.

你不具备使用SUPER,因为你可以给父(在菱形继承的情况下非常有用)的全包名:

sub init {
   my $self = shift;
   $self->ParentClass1::init();
   $self->ParentClass2::init();
}
Run Code Online (Sandbox Code Playgroud)

  • 其他琐事:你实际上可以做`$ self-> TotallyUnrelatedClass :: init()`,虽然它最好不要! (3认同)