gpt4 book ai didi

perl - 如何在 Perl 中使用数组引用中的索引作为方法引用?

转载 作者:行者123 更新时间:2023-12-04 15:27:47 25 4
gpt4 key购买 nike

类似于 this question about iterating over subroutine references ,并且作为回答 this question about a OO dispatch table 的结果,我想知道如何在引用中调用方法引用,而不先删除它,或者是否有可能。

例如:

package Class::Foo;
use 5.012; #Yay autostrict!
use warnings;

# a basic constructor for illustration purposes....
sub new {
my $class = shift;
return bless {@_}, $class;
}

# some subroutines for flavor...
sub sub1 { say 'in sub 1'; return shift->{a} }
sub sub2 { say 'in sub 2'; return shift->{b} }
sub sub3 { say 'in sub 3'; return shift->{c} }

# and a way to dynamically load the tests we're running...
sub sublist {
my $self = shift;
return [
$self->can('sub1'),
$self->can('sub3'),
$self->can('sub2'),
];
}

package main;

sub get_index { ... } # details of how we get the index not important

my $instance = Class::Foo->new(a => 1, b => 2, c => 3);
my $subs = $instance->sublist();
my $index = get_index();

# <-- HERE

因此,在 HERE,我们可以这样做:
my $ref = $subs->[$index];
$instance->$ref();

但是如果不先删除引用,我们将如何做到这一点?

编辑:

更改了代码示例,这样人们就不会纠结于实现细节(叹气,尽力了)。这与我给出的第一个链接之间的重要区别在于该函数应该作为方法调用,而不是作为直接子例程调用。

编辑2:

discussion in the linked comment关于技术细节,以及为什么更长的方式(将子引用存储到变量,然后调用它)可能更可取。

最佳答案

正如所写,你可以逃脱

$tests->[$index]();

因为您问题中的方法没有使用 $self .

你可以通过 $instance明确的,但这很笨拙。更好的是模拟带有闭包的委托(delegate):
sub sublist {
my $self = shift;
my $sublist;
for (qw/ sub1 sub3 sub2 /) {
my $meth = $_;
push @$sublist => sub { $self->$meth() };
}
return $sublist;
}

如果您喜欢简洁,请使用
sub sublist {
my $self = shift;
return [ map { my $meth = $_; sub { $self->$meth() } }
qw/ sub1 sub3 sub2 / ];
}

随机调用一个仍然是
$tests->[$index]();

但现在这些方法得到了调用者。

更新

通过 can 获取子引用似乎是不必要的复杂性。如果运行时确定的要调用的方法名称列表可以,那么您可以大大简化您的代码:
sub sublist {
my $self = shift;
return [ qw/ sub1 sub3 sub2 / ];
}

下面,我们出于测试目的将它们全部调用,但您也可以查看如何只调用一个:
foreach my $method (@$subs) {
my $x = $instance->$method();
say "$method returned $x";
}

输出:

在子 1
sub1 返回 1
在子 3
sub3 返回 3
在子 2
sub2 返回 2

关于perl - 如何在 Perl 中使用数组引用中的索引作为方法引用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2804109/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com