Tutorial de PERL en castellano : Recordando, que es gerundio |
Preguntas frecuentemente preguntadas Bibliografía. Recursos Internet Purgando los pecados. |
split
, matrices asociativas y matrices bidimensionalesAl final del día, nuestro político corrupto reflexiona. ¿De qué sirve tanto trabajo, sin una buena contabilidad consolidada? (Además, tiene que presentarle las cuentas al señor X a fin de mes). Idea, pues, el programa que aparece en el listado 4.
|
Este
programa, aplicado sobre el fichero clientes.mas
, (resultado de una incursión
en la construcción de diversas viviendas para los cuerpos de seguridad
del estado y sus departamentos de investigación y desarrollo, así
como otros procedentes del mundo de la enseñanza) da el siguiente
resultado (o algo parecido)
C:\PROGS\PERL>perl totales.pl clientes.mas Trinque total del dia 3-24 = 598454.75 Trinque total del dia 4-25 = 1100987 Trinque total del dia 4-26 = 487775
Este programa empieza con una
advertencia: "muere si no me metes un fichero como argumento". La orden
die
termina el programa con un mensaje; mientras
que el condicional que lo sigue comprueba que exista al menos un
argumento para el programa;
la matriz @ARGV
contiene los argumentos pasados
al programa; de forma que $#ARGV
dará
el índice del último argumento, o sea que si es -1, indicará
que no se ha pasado ningún argumento. Y otra forma de hacerlo
sería
die "Sin argumento me lamento\n" if $#ARGV < 0;
O incluso
$ARGV[0] || die "Te has quedado sin argumentos\n";
que mira lo que hay a la izquierda del ||
(que es el "o"
lógico), y si es cierto, ejecuta lo que hay a la derecha. Recuerda, en
PERL hay más bla, bla.
El siguiente bucle, que comienza en la línea 2, tiene
una extraña condición para que el bucle siga; sólo
los dos ángulos enfrentados. Teóricamente, debería
de haber un filehandle dentro de esos ángulos (como se
ha visto en un ejemplo anterior), pero en este
caso, se está tomando el fichero por defecto, que es el fichero
que se introduce como argumento; en caso de que no se hubiera introducido
ninguno tomaría entrada estándar, es decir, que habría
que introducirle cada línea mediante teclado. A la vez, y como se
ha visto, esa orden toma una línea del fichero y la deposita en
la variable por defecto, aunque, ojo, no le quita el retorno de carro
final. Hay que tener en cuenta que los paréntesis angulares sin
argumento extraen elementos del array @ARGV
usando
pop
, y abren un fichero con ese nombre; o sea que si
hubiera varios nombres de fichero en la línea de comandos, los iría abriendo uno
por uno y disminuyendo consecuentemente el tamaño de
@ARGV
; conclusión, que si necesitas @ARGV
para algo, mejor que lo guardes antes de meterte en un bucle de esta guisa.
Sobre la variable por defecto actúa la orden split
(una de las cosas más usadas en PERL), dividiéndola en una serie
de cadenas separadas por espacios y depositando cada una de esas cadenas
en un elemento de la matriz @linea
. Y dese
cuenta el venerado público de con qué facilidad hemos hecho
algo que requeriría al menos 10 líneas de cualquier otro
lenguaje. No hay que dimensionar matrices, no hay que recorrer la cadena
caracter por caracter... ¡Nada!(3).
Perdón, me he dejado llevar por el entusiasmo.
La fecha es, en todos los casos, la última cadena de la línea;
es decir, que será el último elemento de la matriz (cuyo
subíndice es siempre $#<nombre-matriz)
),
pero a su vez tendremos que dividirlo, esta vez por la barra de separación,
para luego poder poner el mes delante y que salga todo bellamente ordenado
por meses en vez de por días.
Esta cadena con la fecha, más la pasta, que está siempre 2 posiciones más a la izquierda (independientemente de la longitud de los nombres), se utiliza en la línea 7 en una matriz asociativa. Esta es otra de las características más potentes del PERL, se pueden usar matrices cuyo índice es una cadena cualquiera, no sólo números enteros positivos. Estas matrices asociativas encierran sus índices o claves entre llaves (¿os dáis cuenta del sutil mnemónico?). En esa línea, se le añade al componente de la matriz indexado por la fecha la pasta de la entrada correspondiente. Así, hasta que se termina el fichero de entrada.
Para imprimir el informe, tres cuartos de lo mismo que en el programa
anterior, salvo que en este caso, una matriz asociativa completa se indica
con %
, en vez de la arroba.
|
[v5]A partir de la versión 5 de perl, se pueden usar matrices bidimensionales, mediante un mecanismo que se llama referencias; este mecanismo no nos interesa ahora mismo, pero sí como podemos usarlo en nuestros programas, tales como el siguiente (totales-v5.pl):
|
Este programa es bastante parecido al anterior, salvo que, en vez de almacenarse los resultados en un array asociativo, se almacenan en un array bidimensional; la primera dimensión es el mes, y la segunda representa el día del mes. La línea 2 cambia simplemente para indicar otra forma de detectar si hay un fichero en la línea de comandos o imprimir un mensaje de error.
La línea 7 es la que usa una matriz bidimensional. Hasta aquí, todo
normal; lo único relevante es que no hay que dimensionarla. Como
primer índice de la matriz se usa el elemento 1 de
$linea
, es decir, el mes, y como segundo índice el primer
elemento (el 0), es decir, el día.
Donde sí se nota un cambio es a partir de la línea 10; el bucle lo
hacemos sobre una matriz normal y corriente. El problema es que, tal
como sucede en las matrices bidimensionales en C, en
PERL las matrices bidimensionales son en realidad una
matriz de matrices, o mejor una matriz de referencias. Por eso, en la
línea 11 lo que se hace es dereferenciar el elemento correspondiente y
convertirlo en una matriz que podamos usar, la matriz
@dias
. En la línea 13, usando interpolación, se imprimen
todos los elementos que son no nulos (if
$totalDia[$i][$j]
) la mayoría serán nulos , y los dejamos sin imprimir.
[/v5]
|
[ Preguntas frecuentemente preguntadas] [ Bibliografía.] [ Recursos Internet] [ Purgando los pecados.] |