Как передать функцию, a
, для функции, b
и иметь b
вызов a
в Perl?
Передача объекта функции и вызов его
Ответ 1
Здесь полный рабочий стол script, который демонстрирует, что вы просите.
sub a { print "Hello World!\n"; }
sub b {
my $func = $_[0];
$func->();
}
b(\&a);
Вот объяснение: вы берете ссылку на функцию a
, говоря \&a
. В этот момент у вас есть функция ссылки; в то время как обычно функция вызывается, говоря func()
, вы вызываете ссылку на функцию, говоря $func->()
Синтаксис ->
также относится к другим ссылкам. Например, здесь приведен пример работы с массивами и хеш-ссылками:
sub f {
my ($aref, $href) = @_;
print "Here an array reference: $aref->[0]\n"; # prints 5
print "Here a hash ref: $href->{hello}\n"; # prints "world"
}
my @a = (5, 6, 7);
my %h = (hello=>"world", goodbye=>"girl");
f(\@a, \%h);
Ответ 2
Вы не можете напрямую передать функцию другой функции. Вместо этого вы передаете ссылку на функцию. Чтобы вызвать функцию, вы разыскиваете ее (в качестве ссылки CODE ref) с помощью ->()
;
sub a { print @_ }
sub b {
my $f = shift; # assuming that $f is a function reference...
$f->(@_); # call it with the remaining arguments
}
b(\&a, "hello, world!"); # prints "hello, world!"
Perl не имеет семантики pass-by-name, но вы можете имитировать их с помощью хэша. Метод вызова функции тот же. Вы разыгрываете его.
sub a { print @_ }
sub b {
my %arg = @_;
$arg{function}->(@{$arg{arguments}});
}
b(function => \&a, arguments => ["hello, world!"]);
ObPerl6: Perl 6 будет иметь семантику pass-by-name.
Ответ 3
Вы можете получить доступ к ссылкам подпрограмм как \&my_method
в Perl и вызвать эти ссылки с помощью $myref->();
. Попробуйте следующее:
perl -e'sub a { print "foo in a"; }; sub b { shift->(); }; b(\&a);'
Удачи!
Ответ 4
Следуя примеру Eli Courtwright: если вы используете только одну функцию один раз, вы также можете вызвать b
с анонимной функцией, например:
b( sub { print "Hello World\n"; } );