me gusta pensar en perl -n
como escoger bits específicos de la entrada y perl -p
como map
para todas las líneas de la entrada.
Como se ha observado, es posible conseguir el efecto de -p
con -n
, y podemos emular al revés:
$ echo -e "1\n2\n3" | perl -pe '$_="" if $_ % 2 == 0'
1
3
Saltarse las líneas con next
parecería más natural, pero el código -p
envolturas en
LINE:
while (<>) {
... # your program goes here
} continue {
print or die "-p destination: $!\n";
}
Por diseño, next
corre continue
bloques:
Si hay un BLOQUE continue
, siempre se ejecuta justo antes de que el condicional esté a punto de ser evaluado nuevamente. Por lo tanto, se puede usar para incrementar una variable de bucle, incluso cuando el bucle se ha continuado a través de la instrucción next
.
El interruptor -l
tiene dos efectos prácticos:
- Con
-n
y -p
, automáticamente chomp
cada registro de entrada.
- Conjunto
$\
por lo que cada print
agrega implícitamente un terminador.
Por ejemplo, para agarrar los primeros 10 puertos UDP mencionados en /etc/services
que podría
perl -ane 'print $F[1] if $F[1] =~ /udp/' /etc/services | head
pero oops:
7/udp9/udp11/udp13/udp17/udp19/udp37/udp39/udp42/ud...
Mejor:
$ perl -lane 'print $F[1] if $F[1] =~ /udp/' /etc/services | head
7/udp
9/udp
11/udp
13/udp
17/udp
19/udp
37/udp
39/udp
42/udp
53/udp
Recuerde que -n
y -p
puede estar en la línea shebang también, así que para guardar el oneliner anterior como una secuencia de comandos:
#! /usr/bin/perl -lan
BEGIN {
@ARGV = ("/etc/services") unless @ARGV;
open STDOUT, "|-", "head" or die "$0: head failed";
}
print $F[1] if $F[1] =~ /udp/
'perl -pe' es apropiado para su código de ejemplo. Use '-pe' y suelte la instrucción' print' – mob
Gee, lo aprendí leyendo la salida de 'perl --help'. Tiendo a usar esa opción en todos los programas que uso, solo para saber qué hay disponible. –
Bueno, todo está realmente en perlrun. Todos los hackers de Perl deberían leer la documentación. :) –