Linux en Español

Scripting de bash Parte2 – ciclos For y While con ejemplos

En este tutorial, estudiaremos los  ciclos for y while, y cómo hacer ciclos para iterar sobre una serie de valores.

Ademas, en la publicación anterior, hablamos sobre cómo escribir un script de bash, y vimos que tan increíble es el scripting en bash.

 

El ciclo for

El comando for te permite realizar un ciclo en una lista de elementos. A menudo, esta es la sintaxis fundamental del comando for.

for myvar in vars; do

El código va aquí

done

En cada ciclo, la variable myvar contiene uno de los valores de la lista. El ciclo itera hasta que la lista finaliza.

 

Iterando sobre valores simples

Puedes iterar sobre valores simples como este:

#!/bin/bash

for var in first second third fourth fifth; do

	echo The $var item

done

Verifica los resultados:

ciclos for y while

Iterando sobre valores complejos

Tu lista puede contener una coma o dos palabras, y puedes desear tratarlas como un elemento de la lista.

Observa el siguiente ejemplo:

#!/bin/bash

for var in first "the second" "the third" "I’ll do it"; do

	echo "This is: $var"

done

Encerramos nuestras cadenas de caracteres comillas dobles.

Todo va bien hasta ahora, como siempre. Solo sigue leyendo y practicando.

Iterando sobre valores complejos

 

Sustitución de comando

Al usar la sustitución de comandos utilizando la siguiente sintaxis $ (comando Linux) puedes almacenar el resultado en una variable para usarlo más adelante.

#!/bin/bash

my_file="myfile"

for var in $(cat $my_file); do

	echo " $var"

done

Aquí obtenemos el contenido del archivo usando el comando cat. Ten en cuenta que nuestro archivo contiene una palabra por línea y no están separadas por espacios.

Sustitución de comando

Como podemos observar obtenemos el contenido del archivo utilizando la sustitución de comandos y luego iteramos sobre el resultado, suponiendo que cada línea tiene una palabra.

¿Y qué pasaría si tienes espacios en una de estas líneas?

En este caso, cada palabra se considerará un campo. Necesita decirle al shell que considere el carácter de nueva línea como separador en lugar de los espacios en blanco.

 

El separador de campo

De forma predeterminada, los siguientes caracteres se tratan como campos.

  • Espacio
  • Tabulación
  • Nueva línea

Si tu texto incluye alguno de estos caracteres, el intérprete de comandos asumirá que es un campo nuevo.

Puedes cambiar el separador de campo interno o la environment variable IFS. de esta manera:

IFS=$'\n'

El shell considerará el carácter nueva línea como un separador en lugar de espacios.

#!/bin/bash

file="/etc/passwd"

IFS=$'\n'

for var in $(cat $file); do

	echo " $var"

done

Listo lo lograste. el scripting en Bash es fácil.

Archivo passwd

El separador son los dos puntos en el archivo

/ etc / passwd

  que contiene la información del usuario, puedes asignarlo así:

IFS=:

El scripting en Bash es increíble, ¿verdad?

 

Iteración sobre directorios utilizando el ciclo for

Si deseas listar los archivos en el directorio / home, puede utilizar el ciclo for de esta manera:

#!/bin/bash

for obj in /home/likegeeks/*; do

	if [ -d "$obj" ]; then

		echo "$obj is a folder"

	elif [ -f "$obj" ]; then

		echo "$obj is a file"

	fi

done

En la publicación anterior, conocimos la sentencia if y cómo buscar archivos y carpetas, de modo que, si no sabes, te recomiendo que lo revises script de bash paso a paso.

iteración de directorio

Aquí utilizamos el carácter comodín que es el asterisco * y esto se llama en el globing del archivo de scripts de bash, lo cual significa Todos los archivos con todos los nombres.

Observa que en las sentencias if aquí encerramos nuestras variables con comillas porque tal vez el archivo o el nombre de la carpeta contiene espacios.

En el resultado, se enumeran todos los archivos y directorios en esa carpeta.

 

Ciclo for estilo C

Si conoces el lenguaje C, seguro te parecerá que el ciclo for aquí es un poco extraño porque estás familiarizado con esta sintaxis:

for (var= 0; var < 5; var++)

{

printf(“number is %d\n”, var);

}

Bueno, puedes usar la misma sintaxis, pero con una pequeña diferencia, aquí está la sintaxis.

for ((variable = inicio; condición; paso de iteración))

Entonces se ve así:

for (( var = 1; var < 5; var++ ))

Y este es un ejemplo:

#!/bin/bash

for ((var = 1; var <= 10; var++)); do

	echo "number is $var"

done

Y este es el resultado::

Ciclo for estilo C

 

El ciclo while

El bucle for no es la única forma de hacer ciclos en scripts de bash. El ciclo while hace el mismo trabajo, pero verifica una condición antes de cada iteración.

El comando while tiene la siguiente estructura:

while condición

do

commands

done

Aqui hay un ejemplo:

#!/bin/bash

number=10

while [ $number -gt 4 ]; do

	echo $number

	number=$(($number - 1))

done

El script es simple; comienza con el comando while para verificar si el número es mayor que cero, luego se ejecutará el ciclo y el valor numérico disminuirá cada vez en 1 y en cada iteración de ciclo imprimirá el valor del número, una vez que el valor numérico sea cero el ciclo saldrá.

El ciclo while

Si no disminuimos el valor de var1, tendrá el mismo valor y el ciclo será infinito.

 

Ciclos for y while Anidados

Puede escribir ciclos dentro de ciclos. Esto se llama anidamiento.

Aquí hay un ejemplo de ciclos anidados:

#!/bin/bash

for ((v1 = 1; v1 <= 5; v1++)); do

	echo "Start $v1:"

	for ((v2 = 1; v2 <= 5; v2++)); do

		echo " Inner loop: $v2"

	done

done

El ciclo externo entra primero, luego ingresa al ciclo interno, lo completa y regresa al ciclo externo, y así sucesivamente.

bucles anidados

 

Iterar sobre líneas de archivo

Este es el uso más común para el ciclo for en los scripts bash.

Podemos iterar sobre el contenido del archivo, por ejemplo, iterar sobre el archivo / etc / passwd y ver el resultado:

#!/bin/bash

IFS=$'\n'

for text in $(cat /etc/passwd); do

	echo "This line $text ++ contains"

	IFS=:

	for field in $text; do

		echo " $field"

	done

done

Aquí tenemos dos ciclos, el primero itera sobre las líneas del archivo y el separador es el carácter de nueva línea, la segunda iteración está sobre las palabras en si línea misma y el separador son los dos puntos:

Iterar sobre líneas de archivo

Puedes aplicar esta idea cuando tenga un archivo CSV o cualquier archivo de valores separados por comas. La idea es la misma; solo tienes que cambiar el separador para que se ajuste a tus necesidades.

 

Controlando un ciclo

Tal vez después de que el ciclo comience quieres que se detenga en un valor específico, ¿esperarás hasta que termine el ciclo? Por supuesto que no, hay dos comandos que nos ayudan en esto:

  • El comando break
  • El comando continue

El comando break

El comando break se utiliza para salir de cualquier ciclo, como los while y until.

#!/bin/bash

for number in 10 11 12 13 14 15; do

	if [ $number -eq 14 ]; then

		break

	fi

	echo "Number: $number"

done

El ciclo se ejecuta hasta que llega a 14 y luego el comando break hace que el ciclo salga.

comando break

Y lo mismo para el ciclo while:

#!/bin/bash

val=1

while [ $val -lt 5 ]; do

	if [ $val -eq 4 ]; then # Check number value

		break # The Code Breaks here <==

	fi

	echo "Iteration: $val" # The Printed Message

	val=$(($val + 1))

done

El comando break termina la ejecución del ciclo while y esto ocurre cuando la ejecución alcanza la instrucción if.

bash scripting break while

El comando continue

Puede utilizar el comando continuar para detener la ejecución de los comandos restantes dentro de un ciclo sin salir de este.

Observa el siguiente ejemplo:

#!/bin/bash

for ((number = 1; number < 10; number++)); do # El ciclo comienza aquí

	if [ $number -gt 0 ] && [ $number -lt 5 ]; then # Marque si el número es mayor que 0 y menor que 5

		continue

	fi

	echo "Iteration number: $number" # El mensaje impreso

done

Cuando la condición if es verdadera, el comando continue ejecuta cada iteración, y las líneas después del comando continue nunca se ejecutan hasta que la condición sea falsa.

comando continue

 

Redirigir la salida de un ciclo

Puedes utilizar el comando done para enviar la salida del bucle a un archivo como el siguiente:

#!/bin/bash

for ((var = 1; var < 10; var++)); do

	echo "Number is $var"

done >myfile.txt

echo "finished."

El intérprete de comandos crea el archivo myfile.txt y el resultado se redirige al archivo, si revisamos ese archivo, encontraremos nuestro resultado del ciclo dentro del mismo.

Redirigir la salida de un ciclo

Empleemos nuestro conocimiento de scripts de bash en algo útil.

 

Ejemplos útiles

Encontrar ejecutables

Para obtener todos los archivos ejecutables en tu sistema, puedes recorrer los directorios en la variable PATH. Discutimos las sentencias for e if y el separador de archivos, nuestro conjunto de herramientas está listo así que empecemos. Vamos a combinarlos para hacer algo útil.

#!/bin/bash

IFS=:

for dir in $PATH; do

	echo "$dir:"

	for myfile in $dir/*; do

		if [ -x $myfile ]; then

			echo " $myfile"

		fi

	done

done

Esto es simplemente increíble. Pudimos obtener todos los ejecutables en el sistema.

encontrando ejecutables

Ahora nada te detiene excepto tu imaginación.

Espero que aprendas algo nuevo o al menos refuerces tus conocimientos si lo olvidas. Unas últimas palabras para ti, sigue leyendo y practicando.

Gracias.

Mokhtar Ebrahim
Fundadora de LikeGeeks. Estoy trabajando como administrador de sistemas Linux desde 2010. Soy responsable de mantener, proteger y solucionar problemas de servidores Linux para múltiples clientes de todo el mundo. Me encanta escribir guiones de shell y Python para automatizar mi trabajo.

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *