Si lo que se quiere es construir un array transformado del array inicial, se debe usar map:
@sizes = map {-s $_ } @files;
El operador  -s  retorna el tamaño de un fichero.
Este código genera un array conteniendo los tamaños de los ficheros
especificados en @files. La forma de uso anterior utiliza la sintáxis
map bloque array. Observe la ausencia de coma.
@a = grep { defined } map { /(\d+)/; $1 } glob('/tmp/*')
El operador  glob  produce una lista con los ficheros
descritos por la expresión shell que se le pasa como argumento
(vea perldoc -f glob). La expresión regular /(\d+)/ casa 
con números enteros sin signo. Al estar paréntizada la cadena que ha casado
queda automáticamente guardada en la variable especial $1.
El valor devuelto por un bloque es la última sentencia evaluada, en
este caso es el valor de $1.
Cuando un casamiento con una expresión regular tiene lugar en un contexto de lista se devuelve una lista con las cadenas que han casado con los paréntesis:
  DB<0> $a = "hola 123 b 56 c"
  DB<1> @a = $a =~ m{(\d+)\s(\w+)}
  DB<2> x @a
0  123
1  'b'
  DB<3> @a = $a =~ m{(\d+)\s(\w+)}g
  DB<4> x @a
0  123
1  'b'
2  56
3  'c'
Quizá le ayude a entender la salida la siguiente sesión con el depurador:
  DB<0> x glob('/tmp/*.pl')
0  '/tmp/cgisearch.pl'
1  '/tmp/ficha.pl'
2  '/tmp/uploadpractica.config.pl'
3  '/tmp/uploadpractica.pl'
  DB<1> x map { m{/([^u/]+)$}; $1 } glob('/tmp/*.pl')
0  'cgisearch.pl'
1  'ficha.pl'
2  undef
3  undef
  DB<2> x grep { defined} map { m{/([^u/]+)$}; $1 } glob('/tmp/*.pl')
0  'cgisearch.pl'
1  'ficha.pl'
@a = map { /(\d+)/ } glob('/tmp/*')
produce el mismo resultado que la anterior. ¿Porqué?
¿Que retorna cada una de las evaluaciones individuales 
del bloque? ¿En que contexto lista o escalar se evalúa /(\d+)/?
Observe este comando en el depurador:
 DB<1> x @a = map { /(\d+)/ } ("a123", "b", "c42")
0  123
1  42
@a = map { scalar(/(\d+)/) } glob('/tmp/*')
Casiano Rodríguez León
