Escribamos un módulo B::Simple
que muestre la estructura del árbol
de operaciones:
pp2@nereida:~/src/perl$ perl -MO=Simple -e '$x = 4' LISTOP (0x816d5b0) leave OP (0x8157e60) enter COP (0x816d448) nextstate BINOP (0x816d728) sassign SVOP (0x816d3b8) const UNOP (0x816d408) null PADOP (0x816d5e8) gvsv -e syntax OKEs posible pasarle como opción un número indicándoles la anchura de sangrado:
pp2@nereida:~/src/perl$ perl -MO=Simple,8 -e '$x = 4' LISTOP (0x816d5b0) leave OP (0x8157e38) enter COP (0x816d448) nextstate BINOP (0x816d728) sassign SVOP (0x8157f28) const UNOP (0x816d3e0) null PADOP (0x816d5e8) gvsv -e syntax OKPara ello importaremos del módulo B las funciones
main_root
y walkoptree_slow
.
El módulo B provee varias funciones para recorrer el árbol. La función walkoptree es llamada
walkoptree(OP, METHOD)con un nodo del árbol
OP
y un método METHOD
que es invocado en cada nodo
visitado. No admite pasarle argumentos
adicionales al método, por lo que usaremos una función similar
( walkoptree_slow no documentada) que si lo admite.
En nuestro ejemplo el método print_it
recibe el objeto nodo y el nivel de profundidad
en el árbol. Para convertirlo
en un metodo lo introducimos en el espacio de nombres
B::OP .
pp2@nereida:~/src/perl$ cat -n B/Simple.pm 1 package B::Simple; 2 use B qw(main_root walkoptree_slow); 3 4 my $sep; 5 6 sub B::OP::print_it { 7 my ($self, $level) = @_; 8 9 print "$sep"x$level; 10 printf("%s (0x%x) %s\n", B::class($self), $$self, $self->name); 11 } 12 13 sub compile { 14 $sep = " "x(shift || 3); 15 16 return sub { walkoptree_slow(main_root, "print_it", 0) } 17 } 18 19 1;
Casiano Rodríguez León