问题描述
我一直对 Perl 执行的常量折叠优化感到好奇,但是当代码涉及 Moose 时,很可能不会执行常量折叠(如果我错了,请纠正我).
I've been curious about constant-folding optimizations which Perl performs, but it occurred that when the code has Moose involved chances are that constant-folding won't be performed (please correct me if I am wrong).
我有包含以下方法的 Moose 代码:
I have Moose code which contains the method as below:
sub foo {
my ($self) = shift;
my $test_y = $self->pos->[1];
#...
if ($self->is_map_val($self->pos->[0]+8, $test_y+32) ||
$self->is_map_val($self->pos->[0]+32-8, $test_y+32)) {
{
heavy_stuff();
}
#...
}
当我运行 perl -MO=Deparse ./program.pl
我得到几乎相同的代码行:
and when I run perl -MO=Deparse ./program.pl
I get almost identical code line:
if ($self->is_map_val($self->pos->[0] + 8, $test_y + 32) or
$self->is_map_val($self->pos->[0] + 32 - 8, $test_y + 32))
{
heavy_stuff();
}
我想知道为什么 Perl 没有将 32-8
优化为 24
?Perl 没有这样做是否有任何真正的原因(也许 Moose 子系统让生活变得更艰难?).
I wonder why Perl didn't optimize 32-8
as 24
? Are there any real reasons Perl didn't do that (maybe Moose subsystem makes the life harder?).
如果有帮助,我运行 Perl (v.5.14.2)
If it helps, I run Perl (v.5.14.2)
推荐答案
这与 Moose 无关.在
This has nothing to do with Moose. In
$x + 32 - 8
求值顺序等价于
($x + 32) - 8
(即 +
和 -
具有相同的优先级并且是左关联的).作为一棵树:
(i.e. +
and -
have same precedence level and are left-associative). As a tree:
(-)
/ \
(+) 8
/ \
$x 32
语法树中没有任何部分只有常量节点:$x + 32
不是常量,PREVIOUS_PART - 8
也不是常量.因此,常量折叠(仅在此树级别运行,不能对树的部分重新排序)看不到任何优化机会.
No part of that syntax tree has only constant nodes: $x + 32
isn't constant, and PREVIOUS_PART - 8
isn't constant either. Therefore, the constant folding (which only operates at this tree level, and can't reorder parts of the tree) doesn't see any chances for optimizations.
您确实获得了重新排序为 32 - 8 + $x
的优化.
You do get the optimization of you reorder to 32 - 8 + $x
.
perlguts 文档常量折叠,并特别说明它通过替换部分树来运行.
The perlguts document constant folding, and specifically state that it operates by substituting parts of the tree.
这篇关于Perl 内部结构和 Moose:常量折叠优化的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!