rmi# `while` loop
- `while` loop runs/iterates until test in double brackets is false
- terminates with `done`
- simple example where `-le` corresponds to a less than integer test and `((x++))` increments the x variable by one per iteration
```bash
#!/bin/bash
x=1
while [[ $x -le 10 ]]; do
echo $x
((x++))
done
echo
echo `date`
```
![[images/Pasted image 20250808193451.png]]
# `until` loop
- `until` loop runs/iterates until test in double brackets is true
- similar to `while` loop just the inverse
- terminates with `done`
- simple example where `-le` corresponds to a less than integer test and `((x--))` decrements the x variable by one per iteration
```bash
#!/bin/bash
x=10
until [[ $x -le 1 ]]; do
echo $x
((x--))
done
echo
echo `date`
```
![[images/Pasted image 20250808193707.png]]
- example of string comparison with user input via `read`
- loops until jake/jacob provided as an interactive input
```bash
#!/bin/bash
until [[ $name == @(jake|jacob) ]]; do
echo "Who are you?"
read $name
done
echo "Hi $name! I've been waiting for you"
echo
echo `date`
```
![[images/Pasted image 20250808194215.png]]
# `for` loop
- `for` loops perform an action for items in a list where the list can be a deterministic set of numbers, a range of numbers, set of strings, lines in a file, files in a directory, etc.
- iterates until list is exhausted
- terminates with `done`
- example with deterministic list/set of numbers
- x can be replaced with item or i or anything
```bash
#!/bin/bash
for x in 1 2 3 4; do
echo $x
done
echo
echo `date`
```
![[images/Pasted image 20250808194901.png]]
- example with range of numbers 1-10 with a setp value of 2 `{1..10..2}`
- alternatively `{1..10}` will simply iterate through the whole range with a default step value of 1
```bash
#!/bin/bash
for x in {1..10..2}; do
echo $x
done
echo
echo `date`
```
![[images/Pasted image 20250808195226.png]]
- example where the for loop iterates through strings within a file from the current directory
```bash
#!/bin/bash
for x in $(cat ./names); do
echo $x " marked present"
done
echo
echo `date`
```
![[images/Pasted image 20250808195612.png]]
# loop interruptions
- crtl+c breaks infinite loops
- otherwise add a `break` command to script
- one example of a `break` within an infinite `while` loop
- create infinite while loop with `while true`
```bash
#!/bin/bash
# while true creates an infinite loop
# setup an if conditional breaker inside of the while loop
while true; do
echo "Who are you?"
read name
if [[ $name == "jake" ]]; then
break
fi
echo "Hi - $name!"
done
sleep 1
echo .
sleep 1
echo .
sleep 1
echo .
sleep 1
echo "$name! I bestow upon thee the title: BREAKER OF INFINITE LOOPS"
echo
echo `date`
```
![[images/Pasted image 20250808200544.png]]
- example with a `continue` command (instead of `break`) to perform a specified action at a specified iteration of a `for` loop
- this script skips the third iteration in the range `{1..5}`
```bash
#!/bin/bash
for i in {1..5}; do
if [[ $i -eq 3 ]]; then
continue
fi
echo "Approaching Plant xy-alpha-$i"
sleep 0.5
done
echo
echo `date`
```
![[images/Pasted image 20250808202108.png]]
## real life`for` loop example
- example using `awk` to clean up a command output and creating a script with a `for` loop to remove old docker images ![[images/Pasted image 20250821191301.png]]
- output from `docker images` needs to cleaned up; we only want third field re: image id
- ![[images/Pasted image 20250821191434.png]]
- overwrite existing text file named `images` with `docker images | awk '{print $1}' > images`
- by default the delimiter is a space
- create docker image deletion script based in image_id
```bash
#!/bin/bash
for i in $(cat ./images); do
sudo docker rmi $i 2> /dev/null
done
echo
echo `whoami`
echo `date`
```
![[images/Pasted image 20250821192044.png]]