PERL: БИБЛИОТЕКА ПРОГРАММИСТА - стр. 169
s/\d /| /,
s/["|]/ /g, } if ($Kids{$root}) { в Узел имеет подузлы
my isKids = §{ $Kids{$root} },
@Kids = sort { $Dirsize{$b} <=> $Dirsize{$a} } @Kids,
$Dirsize{$Kids[0]} =- /(\d+)/,
my $width = length $1,
for my $kid (@Kids) { output($kid, $prefix, $width) }
До того как в Perl появилась прямая поддержка хэшей массивов, эмуляция подобных конструкций высшего порядка требовала титанических усилий. Некоторые программисты использовали многократные вызовы split и join, но это работало чрезвычайно медленно.
В примере 5.4 приведена версия программы dutree из тех далеких дней. Поскольку у нас не было прямых ссылок на массивы, приходилось самостоятельно залезать в символьную таблицу Perl. Программа на ходу создавала переменные с жутковатыми именами. Удастся ли вам определить, какой хэш используется этой программой?
5.16. Программа: dutree 177
Массив @{"pcb"> содержит ссылку на анонимный массив, содержащий "pcb/ fix", "pcb/rev' и "pcb/pendmg". Массив @{"pcb/rev"} содержит "pcb/rev/maybe" и "pcb/rev/web". Массив @{"pcb/rev/maybe"} содержит "pcb/rev/maybe/yes" и ¦•pcb/rev/maybe/not'.
Когда вы присваиваете *kid что-нибудь типа 'pcb/f ix", строка в правой части преобразуется в тип-глоб. @kid становится синонимом для @{ 'pcb/f ix"}, но это отнюдь не все. &kid становится синонимом для &{" pcb/f ix"} и т. д.
Если эта тема покажется неинтересной, подумайте, как local использует динамическую область действия глобальных переменных, чтобы избежать передачи дополнительных аргументов. Заодно посмотрите, что происходит с переменной width в процедуре output.
Пример 5.4. dutree-orig
tt> /usr/bm/perl
# dutree_orig старая версия, которая появилась
й до выхода perl$ (начало 90-х)
(alines = du @ARGV ,
chop(@lines),
&input($top = pop @lines),
&output($top),
exit,
sub input {
local($root, *kid, $him) = @_[0,0],
