Довольно редко вам действительно нужно делать что-то подобное, обычно это признак того, что вы копаетесь в объекте таким образом, что вы снова будете кусать вас позже.Если это действительно то, что нужно сделать, вы можете изменить свой пакет только для вызова метода, чтобы изменить то, что видит SUPER, или переопределить поиск метода, вызвав полное имя метода.
{
package BaseClass;
sub new { bless \my $self, shift; }
sub foo {
my $self = shift;
print "BaseClass::foo()\n";
}
}
{
package SubClass;
our @ISA = qw(BaseClass);
sub foo {
my $self = shift;
print "SubClass::foo()\n";
$self->SUPER::foo();
}
}
{
package ParentClass;
sub new { bless \my $self, shift; }
sub bar {
my $self = shift;
print "ParentClass::bar()\n";
}
}
{
package ChildClass;
our @ISA = qw(ParentClass);
sub foo {
my $other = SubClass->new();
print "ChildClass::foo()\n";
# fails trying to find ParentClass::foo()
eval { $other->SUPER::foo(); } or warn $@;
# thinks this is SubClass and finds BaseClass::foo()
{ package SubClass; $other->SUPER::foo(); }
# if you know the correct class that SUPER::foo() would have called (but this will also work if it was the wrong class)
$other->BaseClass::foo();
}
sub bar {
my $self = shift;
print "ChildClass::bar()\n";
$self->SUPER::bar();
}
}
my $obj_1 = SubClass->new();
$obj_1->foo();
my $obj_2 = ChildClass->new();
$obj_2->bar();
$obj_2->foo();
Более чистым вариантом являетсяреорганизовать ваши методы, чтобы вы могли обращаться к методам как базового класса, так и подкласса, не пытаясь разрушить объектную систему.
{
package BaseClass;
sub new { bless \my $self, shift; }
sub foo {
my $self = shift;
print "BaseClass::foo()\n";
}
}
{
package SubClass;
our @ISA = qw(BaseClass);
sub bar {
my $self = shift;
print "SubClass::bar()\n";
$self->SUPER::foo();
}
}
my $obj = SubClass->new();
$obj->foo();
$obj->bar();
Или предоставить метод для вызова метода базового класса.
{
package BaseClass;
sub new { bless \my $self, shift; }
sub foo {
my $self = shift;
print "BaseClass::foo()\n";
}
}
{
package SubClass;
our @ISA = qw(BaseClass);
sub foo {
my $self = shift;
print "SubClass::foo()\n";
$self->SUPER::foo();
}
sub bar {
my $self = shift;
$self->SUPER::foo();
}
}
my $obj = SubClass->new();
$obj->foo();
$obj->bar();
Лучший ответ на самом деле зависит от того, что вы действительно пытаетесь сделать, и почему для этого необходимо обходить стандартное наследование.