gpt4 book ai didi

perl - 嵌套子前的神秘 *

转载 作者:行者123 更新时间:2023-12-04 16:44:37 24 4
gpt4 key购买 nike

* 在 _fact 前面的确切功能/目的是什么以及如何等效地编写它?

sub fact {
my ($n) = @_;

local *_fact = sub {
my ($n, $prod) = @_;
return $prod if $n == 0;
return _fact($n-1, $n*$prod);
};

return _fact($n, 1);
}

fact($n);

最佳答案

理想情况下,函数的作者希望使用

sub fact {
my ($n) = @_;

my $_fact; $_fact = sub {
my ($n, $prod) = @_;
return $prod if $n == 0;
return $_fact->($n-1, $n*$prod);
};

return $_fact->($n, 1);
}

不幸的是,这有内存泄漏。 anon sub 引用了 $_fact ,它持有对匿名子的引用。 $_fact需要清除以在退出时中断引用。
sub fact {
my ($n) = @_;

my $_fact;
$_fact = sub {
my ($n, $prod) = @_;
return $prod if $n == 0;
return $_fact->($n-1, $n*$prod);
};

my $rv;
my $e = eval { $rv = $_fact->($n, 1); 1 } ? undef : ($@ || 'Unknown');
$_fact = undef;
die $e if $e
return $rv;
}

但这太丑了!避免该问题的一种方法是使用 Y combinator .避免该问题的更简单的方法是将代码引用存储在包变量而不是词法变量中(因为 subs 只捕获词法变量)。这就是您发布的代码所做的。请记住
*_fact = sub { ...  };

基本上是一个运行时版本
sub _fact { ... }

两者都将 sub 分配给符号 _fact 的 CODE 槽.

也就是说,5.16 引入了一个更好的修复:
use feature qw( current_sub );

sub fact {
my ($n) = @_;

my $_fact = sub {
my ($n, $prod) = @_;
return $prod if $n == 0;
return __SUB__->($n-1, $n*$prod);
};

return $_fact->($n, 1);
}

关于perl - 嵌套子前的神秘 *,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19777251/

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