glob
permite la expansión de los comodines de la shell.
Asi en una expresión como:
my @all_files = glob "*";la variable
all_files
guarda ordenados
alfabéticamente la lista de los nombres de los ficheros en el directorio actual.
Es posible, como indica el siguiente ejemplo utilizar varios patrones separados por espacios.
my @including_hidden = ".* *";
Usar glob
es mas eficiente y mas portable que enviar el requerimiento a la
shell del sistema usando backticks (como por ejemplo en `ls .*`
).
Cuando en el operador de lectura <>
el argumento es una cadena glob
de descripción de ficheros con comodines, el globbing se produce automáticamente:
my $dir = "/home/casiano/"; my $dir_files = <$dir/* $dir/.*>;
También puede hacerse en un contexto de lista:
DB<1> @modules = <*.pm> DB<2> p "@modules" A.pm Abstract.pm B.pm C.pm DandC.pm Frac.pm Fraction.pm
En general, si el identificador entre ángulos es un filehandler, Perl hace un acceso a través de él, en caso contrario interpreta que se trata de una operación de globbing. Esto es asi, incluso si la lectura hace uso de un manipulador indirecto que use variables intermedias. Véase el siguiente ejemplo:
DB<1> $f = 'yapp' DB<2> @f = <$f/*.yp> DB<3> p "@f" yapp/aSb.yp yapp/Autoaction1.yp yapp/Calc.yp yapp/Calc2.yp DB<4> open F, 'logic.pl' DB<5> $x = F DB<6> @x = <$x> DB<7> p "@x" #!/usr/bin/perl -w $a = 4; $b = "hola"; $c = 0; $d = ""; print $a && $b,"\n"; print $a and $b,"\n"; print ($a and $b),"\n";
Obsérve que en un bucle for (list) el argumento list se evalúa en un contexto de lista.
my $bytes = 0; for (<*.c>) { $bytes += -s }En este código, la lectura del directorio
<*.c>
se produce en un
contexto de lista. Por ello el directorio completo es leído y produce una lista con todos los
nombres de ficheros *.c
existentes en el directorio actual. El subsecuente
proceso iterativo acumula en $bytes
el tamaño de los ficheros *.c
.
En ocasiones es importante distinguir entre falsedad e indefinición, como en este ejemplo:
while ($file = <*>) { do_something($file); }En este código, en cada pasada del bucle el operador
<*>
produce
un nuevo nombre de fichero del directorio actual. El nombre es asignado a
$file
. ¿Que ocurre si el nombre del fichero es "0"
?.
En tal caso el bucle tendrá una ``muerte'' prematura. La codificación
correcta sería:
while (defined($file = <*>) { do_something($file); }Sin embargo, siguiendo la filosofía de ``ayudar'' al programador, las últimas versiones de Perl tiene el comportamiento ``esperado''. Esto es, detectan el uso en un
while
del glob
e interpretan que "0"
como nombre de fichero no
es falso. Sin embargo en otro contexto, "0"
si se interpreta como falso. Observe
el siguiente ejemplo:
$ cat muerte_prematura2.pl #!/usr/bin/perl -w my $file; my @a = ("uno","0","dos"); while ($file = shift @a) { do_something($file); } sub do_something { print "$file\n"; }Al ejecutar obtenemos:
$ ./muerte_prematura2.pl uno