Por ejemplo, ante la entrada:
4 5 2 + *
El programa deberá imprimir 28
.
Sugerencias:
STDIN
:
local $_ = shift || do { print 'postfix expression: '; <STDIN> };recuerde proteger con comillas simples el argumento si lo provee desde la línea de comandos:
split
.
Recuerde que la expresion regular \s
casa con cualquier blanco
Puede consultar la tabla en la sección 3.6.
lhp@nereida:~/Lperl/src$ perl -wde 0 main::(-e:1): 0 DB<1> x split /\s+/, "2 3 7 + * 4 -" 0 2 1 3 2 7 3 '+' 4 '*' 5 4 6 '-'
La siguiente sesión con el depurador sugiere una aproximación:
DB<1> $x = "2 13+2*3-" DB<2> @tokens = split /\s+|\b/, $x DB<3> x @tokens 0 2 1 13 2 '+' 3 2 4 '*' 5 3 6 '-'
El ancla \b
casa con una frontera de palabra. ¿Es suficiente con este arreglo?.
DB<4> $x = "2 b+2*;3-" DB<5> @tokens = split /\s+|\b/, $x DB<6> x @tokens 0 2 1 'b' 2 '+' 3 2 4 '*;' 5 3 6 '-'
Intente controlar los errores.
when (/^\d+$/) { push @stack, $_; next; }
[-+*/]
).
when (m{^[-+/*]$}) { my $b = pop @stack or die("Missed arg for '$_'!\n"); ... next; }
=~
si es necesario.
die
puede utilizarse para abortar la
ejecución de un programa. Observe estos dos ejemplos de uso:
$op1 = pop @stack or die("Faltan argumentos\n"); ($x != 0) or die "No se puede dividir por cero!\n";
DB<1> $x = '4 + 2' DB<2> p $x 4 + 2 DB<3> $y = eval($x) DB<4> p $y 6 DB<5> p eval('3+$y') 9 DB<6> $a = 4 DB<7> $b = 5 DB<8> $op = '*' DB<9> print "$a $op $b" 4 * 5 DB<10> print eval "$a $op $b" 20Para saber mas sobre la función eval consulte la documentación escribiendo
perldoc -f eval
.
*
y +
son metasímbolos dentro de una expresión regular pero no
dentro de una clase.
$&
almacena la cadena que casó con la última expresión
regular usada, $1
, $2
, etc. contienen las cadenas que casaron con los paréntesis
que aparecen en la expresión regular.
Casiano Rodríguez León