賦予一個編碼裁判,是有可能:如何通過指定其分析樹來創建perl子?
- 接入代碼ref的解析樹
- 通過指定代碼ref的解析樹可以包含解析的元素創建一個新的代碼REF樹在
返回通常我們通過指定的源代碼,然後將其解析並轉換成一個解析樹創建在Perl子程序。
我想寫一個perl函數,它可以通過指定其分析樹來創建一個子例程,並且該分析樹可以從另一個子例程的其他分析樹中派生。
可能嗎?
賦予一個編碼裁判,是有可能:如何通過指定其分析樹來創建perl子?
返回通常我們通過指定的源代碼,然後將其解析並轉換成一個解析樹創建在Perl子程序。
我想寫一個perl函數,它可以通過指定其分析樹來創建一個子例程,並且該分析樹可以從另一個子例程的其他分析樹中派生。
可能嗎?
我不知道你的問題的完整答案,但我知道Data :: Dumper可以deparse一個代碼引用。看看它的文檔,我發現它使用B::Deparse
來完成繁重的工作(B::
模塊是與編譯器交互的模塊)。不幸的是,這似乎只會導致coderef的文本表示。
而是我在metacpan上搜索了Op
,並獲得了更多有趣的可能性。由於我現在已經遠離了我最深刻的Perl魔法,所以我會讓你看看這些結果。也許有些東西會有用。
感謝您的「歐普」。我想使用閉包,所以我確定有必要訪問分析樹中的底層節點,以便創建新的閉包,這些閉包在相同的變量上關閉。 – ErikR
請確保你查看['PadWalker'](http://p3rl.org/PadWalker),我想這是很多人用來調查關閉的。 –
這與操作碼無關,但它在三個不同的閉包中包含了相同的兩個變量。變量被包含在讓人想起類的get/set例程的子例程中,然後這些關閉的變量通過其訪問例程被其他閉包共享。
這是對評論的回覆:我確定有必要訪問分析樹中的底層節點,以便我可以創建新的閉包,這些閉包在相同的變量上關閉。
use strict;
use warnings;
use v5.14;
# create closed vars
my $v1 = access_closure(6);
my $v2 = access_closure(42);
# play with them
say "v1 ", &$v1;
say "v2 ", &$v2;
say "v1 ", &$v1(5);
say "v2 ", &$v2(43);
say "v1 ", &$v1;
say "v2 ", &$v2;
# create silly closures that use them
my $test1 = test_closure(2);
my $test2 = test_closure(17);
my $test3 = test_closure(50);
# play with those
&$test1;
&$test2;
&$test3;
# create the get/set routine for a closed var
sub access_closure {
my $val = shift;
return sub {
$val = shift if @_;
return $val;
}
}
# create a silly closure that encloses a control var and uses the two other vars
sub test_closure {
my $val = shift;
return sub {
say "\nval is $val";
printf "v1 is %2d, v2 is %2d\n",
&$v1, &$v2;
if (&$v1 < $val) {
say "Increment v1";
&$v1(&$v1+1);
}
if (&$v2 > $val) {
say "Decrement v2";
&$v2(&$v2-1);
}
printf "v1 is %2d, v2 is %2d\n",
&$v1, &$v2;
}
}
一方面一個迷人的問題。另一方面,聽起來像是有些東西跑不走。我很好奇你的用例是什麼? –
Yous說:「解析樹可以從其他子程序的另一個解析樹中派生出來」,但你的問題完全與此無關。你究竟在做什麼? – ikegami