Perl en Español

  1. Home
  2. Tutoriales
  3. Foro
  4. Artículos
  5. Donativos
  6. Publicidad
 

Pasar a una variable solamente parte de una cadena de texto

 
Publicar nuevo tema   Responder al tema    Foros de discusión -> Básico
Mensaje Jue Abr 24, 2008 4:29 am
xiuron
Perlero Nuevo
Perlero Nuevo
Registrado: 24 Abr 2008
Mensajes: 3
Pasar a una variable solamente parte de una cadena de texto Responder citando

Hola,

Soy nuevo en el foro (y en Perl Embarassed ); soy Javi... ¡ Encantado !.

Quiero usar Perl para simplificar algunas tareas de administración, pero me quedo pillado en cosas que seguramente sean muy simples.

He hecho un código para que el resultado de un comando sea almacenado en una variable. Pero de esta variable solo quiero un "trocito", me explico, quiero por ejemplo saber el nivel de "idle" de mi servidor. Mi código es este:

Perl:
# !/usr/bin/perl

### Declaracion de variables ###
my $cpu;

### Asignacion de valores ###

$cpu= `top -n 1 | grep Cpu`;

### Salida por pantalla ###

# AQUI ME PIERDO JEJE

print "\n";


Pues eso... con top -n 1 | grep Cpu paso solo la línea de CPU del comando TOP, pero aun así me da a la variable muchas más cosas que el " 99" por ejemplo que quiero...

¿Como puedo coger solo los "dígitos" que yo quiera de una cadena de texto?

Gracias por ayudarme Smile
Mensaje Jue Abr 24, 2008 5:21 am
explorer
Moderador
Moderador
Registrado: 24 Jul 2005
Mensajes: 4082
Ubicación: Valladolid, España
Responder citando

Bienvenido a los foros de Perl en Español, xiuron.

Se te ha pasado un detalle. top es un programa fundamentalmente interactivo y que, además, utiliza caracteres de control para pintar en toda la pantalla.

Bueno, resulta que si aplicamos una expresión regular para extraer la información que quieres:

bash:
explorer@joaquin:~/Documents/Desarrollo> perl -le '$top = qx(top -n 1|grep Cpu); ($idle) = $top =~ m/([0-9.]+)\%id,/; print "->$top<-:->$idle<-"'


no sale nada.

Es debido a que top está sacando caracteres de control para colocar y colorear las cifras que mostraría en la terminal:

Código:
explorer@joaquin:~/Documents/Desarrollo> top -n 1 |grep Cpu |hexdump -C
00000000  43 70 75 28 73 29 3a 1b  28 42 1b 5b 6d 1b 5b 33  |Cpu(s):.(B.[m.[3|
00000010  39 3b 34 39 6d 1b 28 42  1b 5b 6d 20 20 37 2e 35  |9;49m.(B.[m  7.5|
00000020  25 1b 28 42 1b 5b 6d 1b  5b 33 39 3b 34 39 6d 75  |%.(B.[m.[39;49mu|
00000030  73 2c 1b 28 42 1b 5b 6d  1b 5b 33 39 3b 34 39 6d  |s,.(B.[m.[39;49m|
00000040  1b 28 42 1b 5b 6d 20 20  30 2e 38 25 1b 28 42 1b  |.(B.[m  0.8%.(B.|
00000050  5b 6d 1b 5b 33 39 3b 34  39 6d 73 79 2c 1b 28 42  |[m.[39;49msy,.(B|
00000060  1b 5b 6d 1b 5b 33 39 3b  34 39 6d 1b 28 42 1b 5b  |.[m.[39;49m.(B.[|
00000070  6d 20 20 31 2e 30 25 1b  28 42 1b 5b 6d 1b 5b 33  |m  1.0%.(B.[m.[3|
00000080  39 3b 34 39 6d 6e 69 2c  1b 28 42 1b 5b 6d 1b 5b  |9;49mni,.(B.[m.[|
00000090  33 39 3b 34 39 6d 1b 28  42 1b 5b 6d 20 38 39 2e  |39;49m.(B.[m 89.|
000000a0  30 25 1b 28 42 1b 5b 6d  1b 5b 33 39 3b 34 39 6d  |0%.(B.[m.[39;49m|
000000b0  69 64 2c 1b 28 42 1b 5b  6d 1b 5b 33 39 3b 34 39  |id,.(B.[m.[39;49|
000000c0  6d 1b 28 42 1b 5b 6d 20  20 31 2e 37 25 1b 28 42  |m.(B.[m  1.7%.(B|
000000d0  1b 5b 6d 1b 5b 33 39 3b  34 39 6d 77 61 2c 1b 28  |.[m.[39;49mwa,.(|
000000e0  42 1b 5b 6d 1b 5b 33 39  3b 34 39 6d 1b 28 42 1b  |B.[m.[39;49m.(B.|
000000f0  5b 6d 20 20 30 2e 30 25  1b 28 42 1b 5b 6d 1b 5b  |[m  0.0%.(B.[m.[|
00000100  33 39 3b 34 39 6d 68 69  2c 1b 28 42 1b 5b 6d 1b  |39;49mhi,.(B.[m.|
00000110  5b 33 39 3b 34 39 6d 1b  28 42 1b 5b 6d 20 20 30  |[39;49m.(B.[m  0|
00000120  2e 30 25 1b 28 42 1b 5b  6d 1b 5b 33 39 3b 34 39  |.0%.(B.[m.[39;49|
00000130  6d 73 69 2c 1b 28 42 1b  5b 6d 1b 5b 33 39 3b 34  |msi,.(B.[m.[39;4|
00000140  39 6d 1b 28 42 1b 5b 6d  20 20 30 2e 30 25 1b 28  |9m.(B.[m  0.0%.(|
00000150  42 1b 5b 6d 1b 5b 33 39  3b 34 39 6d 73 74 1b 28  |B.[m.[39;49mst.(|
00000160  42 1b 5b 6d 1b 5b 33 39  3b 34 39 6d 1b 5b 4b 0a  |B.[m.[39;49m.[K.|
00000170
La información que queremos está ahí, pero mezclada con caracteres de control de presentación en terminal.

La solución pasa primero por intentar quitar esos caracteres de control. En la página man del top nos da la pista: la opción -b sirve para encauzar la salida del comando a otros programas.

Bueno, pues se lo agregamos:
bash:
explorer@joaquin:~/Documents/Desarrollo> perl -le '$top = qx(top -b -n 1|grep Cpu); ($idle) = $top =~ m/([0-9.]+)\%id,/simo; print "->$top<-:->$idle<-"'
y ya sale la cifra correcta.

El programa Perl que estamos ejecutando es este:
Perl:
#!/usr/bin/perl
$top = qx(top -b -n 1|grep Cpu);
($idle) = $top =~ m/([0-9.]+)\%id,/;
print "->$top<-:->$idle<-\n"
La captura de la parte 'idle' se hace por medio de una expresión regular (m//), aplicada a la variable $top. Lo que hace es: queremos capturar (()) todo (+) lo que se parezca a un número ([0-9.]) que preceda a la cadena %id,. Esta captura, de hacerse, debe pasar a la primera variable del array que se encuentre a la izquierda de esta operación. Ese array es ($idle), por lo que guardará en esa variable lo capturado (o lo dejará indefinido).

Aprender expresiones regulares es uno de los 3 pilares de la programación en Perl. Parece farragoso, pero ya ves que soluciona problemas en muy poco sitio y rápidamente.

¡Adelante!

Actualización: Naturalmente, en Perl hay muchas formas de hacerlo. Así que otra forma más es la más inmediata de todas: como la información está en posiciones fijas, sabemos entonces cómo extraerlas:
bash:
joaquin:/etc/joe > perl -le 'print substr(qx(top -b -n 1|grep Cpu), 35, 5)'
88.2%

Eso sí... Perl es conocido también por su adaptación a los cambios del entorno. Si un día cambia de funcionar el comando, es muy posible que con la primera solución siga trabajando, ya que no estamos indicando posiciones exactas, sino coincidencia de patrones.
Mensaje Jue Abr 24, 2008 8:14 am
xiuron
Perlero Nuevo
Perlero Nuevo
Registrado: 24 Abr 2008
Mensajes: 3
Responder citando

Gracias amigo,

Yo lo había solucionado mirando por diversas web de esta manera:

Perl:
my cpu= `top -n 1 | grep Cpu`;
my $cpuc = substr $cpu, -22, 4;


Pero, leyendo lo que me cuentas, veo que ésta es una manera un tanto "cutre" de hacerlo; me interesa bastante más la primera manera que cuentas... ¡Voy a estudiarla!

Gracias... Javi Wink
Mensaje Jue Ago 07, 2008 12:18 pm
Kiloko
Perlero Adicto
Perlero Adicto
Registrado: 10 Jul 2007
Mensajes: 244
Ubicación: MOnterrey NL
Responder citando

Eso suena superbien. Es más o menos lo que estoy buscando pero con un Df -K... voy a ver si puedo adaptar lo que propones...

Saludos
Publicar nuevo tema   Responder al tema    Foros de discusión -> Básico Todas las horas son GMT - 6 Horas
Página 1 de 1



Powered by phpBB © 2001, 2005 phpBB Group