2009-09-21 20 views
8

Podría hacer esto en cualquier otro idioma, pero con Bash he buscado mucho y no he podido encontrar la respuesta.iterar manualmente una línea de un archivo | bash

Necesito manualmente aumentar $line en un script. Ejemplo:

for line in `cat file` 
do 
foo() 
     foo_loop(condition) 
{ 
do_something_to_line($line) 
} 
done 

Si se fijan, cada vez que el foo_loop itera, $line sigue siendo el mismo. Necesito iterar $line allí, y me aseguro de que el bucle original for solo ejecuta el número de líneas en el archivo.

He pensado en encontrar el número de líneas en el archivo utilizando un ciclo diferente e iterando la variable de línea dentro del ciclo interno de foo().

¿Alguna idea?

EDIT:

Lo siento por ser tan vago.

Aquí vamos:

que estoy tratando de hacer una sección de mi código de ejecutar varias veces (ejecución paralela)

Function foo() # Does something 
for line in `cat $temp_file`; 
foo($line) 

Ese código funciona bien, porque foo simplemente se está llevando en el valor de línea; pero si lo que quería hacer esto:

Function foo() # Does something 
for line in `cat $temp_file`; 
while (some condition) 
foo($line) 
end 

$line será igual al mismo valor en todo el bucle while. Necesito que cambie con el ciclo while, luego continúo cuando vuelva al for. Ejemplo:

line = Hi 
foo{ echo "$line" }; 
for line in `cat file`; 
while (number_of_processes_running -lt max_number_allowed) 
foo($line) 
end 

Si el contenido del archivo eran

Hi \n Bye \n Yellow \n Green \n 

La salida del programa de ejemplo sería (si el número máximo permitido fue 3)

Hi Hi Hi Bye Bye Bye Yellow Yellow Yellow Green Green Green. 

donde quiero que a ser

Hi Bye Yellow Green 

Espero esta es mejor. Estoy haciendo mi mejor esfuerzo para explicar mi problema.

+0

Creo que necesitamos un ejemplo más claro de lo que estás tratando de lograr. foo() parece definir una función de shell dentro de un bucle, de lo que no estoy seguro es lo que quieres. –

Respuesta

16

En lugar de utilizar un bucle for para leer el archivo, tal vez deba leer el archivo como tal.

#!bin/bash 

while read line 
do 
    do_something_to_line($line) 
done < "your.file" 
+0

Tenga en cuenta que esto no funcionará para las líneas con barras diagonales inversas (la lectura las elimina) y los espacios en blanco iniciales y/o finales (eliminados también). La forma correcta es usar 'read -r line' para evitar la eliminación de la barra invertida y establecer' IFS = 'para evitar la eliminación del espacio en blanco. – Jens

6

Para resumir, while read line; do _____ ; done

A continuación, asegúrese de que usted tiene comillas alrededor de "línea $" para que un parámetro no está delimitado por espacios.

Ejemplo:

$ cat /proc/cpuinfo | md5sum 
c2eb5696e59948852f66a82993016e5a *- 

$ cat /proc/cpuinfo | while read line; do echo "$line"; done | md5sum 
c2eb5696e59948852f66a82993016e5a *- 

Segundo ejemplo # añaden.gz a cada archivo en el directorio actual: # Si los archivos tienen espacios, el comando mv para esa línea devolverá un error.

$ find -type f -maxdepth 1 | while read line; do mv "$line" "$line.gz"; done 
+1

-1 para el uso inútil de cat. ¿Sabía que puede redirigir a comandos compuestos también? 'mientras lee ...; hacer ... hecho Jens

1

Debe publicar los seguimientos como ediciones a su pregunta o en los comentarios en lugar de una respuesta.

esta estructura:

while read line 
do 
    for ((i=1; i<$max_number_allowed; i++)) 
    do 
     foo $line 
    done 
done < file 

Rendimiento:

Hi 
Hi 
Hi 
Bye 
Bye 
Bye 
...etc.

mientras éste:

for ((i=1; i<$max_number_allowed; i++)) 
do 
    while read line 
    do 
     foo $line 
    done < file 
done 

Rendimiento:

Hi 
Bye 
Yellow 
Green 
Hi 
Bye 
Yellow 
Green 
...etc.
Cuestiones relacionadas