Linux Bash Scripting Tutorial
A Loop is a iterative(repetetive) block of commands runs as long as control condition is true
Bash supports the following looping constructs
This is a basic looping constructs in bash shell. Popular looping construct, versatile syntax looping any list of values, or arrays.
for loop syntax
for arg in [list] do command(s); done;
Here [list] of items/array of items are optional. if [list] is empty/nulls reads input from command line i.e positional parameters
for loop example:
for i in 1 2 3 4 5 do echo -n $i ' ' done output 1 2 3 4 5
For each iteration variable i contains one value from the list
here [list] is 1 2 3 4 5
1st Iteration i has value 1
2nd Iteration i has value 2 etc.,
IFS -Internal Field seperator by default set to space.
User can set any symbol other than space.
Here IFS set to color(:) as delimiter, in above case space is the delimiter
IFS=':' for i in 1:2:3:4:5 do echo -n $i ' ' done output 1 2 3 4 5
Wild character in for loop list
In this for loop , list has a b * c d, note: whenever loop sees wild card '*' , bash performs file expansion, similarly `ls *`. In ls * , lists all files ,sub directory files recursively. where as in for loop, displays only current directory's files and sub-directories.
for i in a b * c d do echo -n $i ' ' done
'C' langauage style - for loop syntax
for (( expression1; condition; expression2)) do command(s); done;
expression1 initial value. expression2 increment/decrement the value(s) loop iterates till condition is false
'C' langauage for loop example:
printing numbers from 1 to 10
for (( i=1 ; i <= 10 ; i++) do echo -n $i ' ' done echo output 1 2 3 4 5 6 7 8 9 10
printing numbers from 10 to 1
for (( i=10 ; i >=1 ; i--)) do echo -n $i ' ' done echo output 10 9 8 7 6 5 4 3 2 1
Reverse a String using For Loop
Algorithm:#!/usr/bin/bash #************************************************* # THis Program Reverses a String using For Loop #************************************************* name='Rust programming' length=${#name} for (( i=-1 ; i != -(length+1) ; i--)) do reverse+=${name:(i):1} done echo "Orginal String: ${name}" echo echo "Reversed String: ${reverse}" echoOutput:
Orginal String:Rust programming Reversed String:gnimmargorp tsuRfind . -iname *.cpp -print0 will print null-seperated file names.recall that this helps, if the filenames have spaces in them
This construct tests for a condition on top of a loop, and keeps looping as long as that condition is true
while loop syntax:
while [condition] do command(s) done[< file]
while loop Example:
Display numbers from 1 to 10 using while loop
1. i=1 2. while [ $i -lq 10 ] 3. do 4. echo -n $i ' ' 5. let "i++" 6. done; 7. echo
Line 1: Variable i set to 1
Line 2: while loop condition, $i -lq 10 -lq is less than or equal to
if i value less than or equal to 10 then it enter into loop
Line 4: print value i
Line 5: increment i value by 1 using post-increment operator and using let command.
Loop repeates from Line 2 - 5 for 10 times, when i value greater than 10,means condition is false,breaks the loop
Reading a File using While loop using Input redirection Operator( < ). It is possible when you combine with Read command and in any loop. Loop continues until EOF(End Of File) is encountered.
Note: Read command reads entire line or a specified fields.
$ cat stocks.txt symbol company previous today's date ------------------------------------------------- msft microsoft 247.11 241.55 2014-09-15 amzn amazon 100.79 98.49 2018-01-20 fb facebook 113.02 114.22 2016-03-15 ko cocacola 61.32 60.73 2020-11-15
FILE="stocks.txt" NEW_FILE="stocks_new.txt" :>File truncates the file #echo "">"$NEW_FILE" :>"$NEW_FILE" lc=0; #read fields while read symbol company prev today dt do #ignore header let "lc = lc+1" if test $lc -le 2; then continue; fi #trade gain or loss change=$(echo $today-$prev | bc) #trade gain or loss percentage perct=$(echo "scale=2;$change*100/$prev" | bc) #write into a new file echo -e "${symbol^^}\t$prev\t$today\t$change\t${perct}%\t$dt">>"$NEW_FILE" done < $FILE
$ cat stocks_new.txt MSFT 247.11 241.55 -5.56 -2.25% 2014-09-15 AMZN 100.79 98.49 -2.30 -2.28% 2018-01-20 FB 113.02 114.22 1.20 1.06% 2016-03-15 KO 61.32 60.73 -.59 -.96% 2020-11-15
Here Document represents multi-line text , it has special syntax to represent text spanned across multiple Lines
cmd<<NAME some line(s) NAME #Mark end of the Document
cmd <<DOCUMENT line 1 line 2 line 3 . . . line N DOCUMENT
While Loop is going to read multiple Lines from Here Document
while read line do echo $line done <<DOCU #Here Document Starting This is first line This is second line This is Third line This is fourth line DOCU #Here Document Ending
Execute the Above script. output will be
This is first line This is second line This is Third line This is fourth lineNote: Above Here Doc has static text.Here document can also be build dynamically using parameter expansions/shell expansions
This construct tests for a condition on top of a loop, and keeps looping as long as that condition is false, just opposite of while loop
until loop syntax:
until [condition-is-true] do command(s) done
until loop example:
displaying numbers from 1-10 using until loop in bash
1. declare -i i=1; 2. until [ $i -eq 11 ] 3. do 4. echo -n $i ' ' 5. let "i = i+1" 6. done 7. echo
output:1 2 3 4 5 6 7 8 9 10
Explanation:
Line 1 : declare integer variable and initialize it with 1
Line 2 : until loop condition, if condition is false then it enters into loop executes commands, if false exits from the loop
Line 3: i equals to 1 and not equal to 11, so it enters into loop
Line 4: prints value i using echo command
Line 5: Increment value i by 1 using let arithmetic command.
repeate Line 2-5 for 10 times, in 11th iteration it matches with condition and condition is said to be true breaks the loop
commands affecting loop behavior
break andcontinue loop control commands
break commands terminates the loop(breaks out of the loop)
continue commands causes a jump to the next iteration of the loop,skipping all remaining commands next to it.
continue command example:
print even numbers from 1 to 10
1. for i in {1..10} 2. do 3. if [[ $(($i % 2)) -ne 0 ]]; 4. then 5. continue; 6. fi 7. echo -n $i ' ' 8. done 9. echo
continue command example 2:
This example displays directory names,
d=$(file -b "$i") , file command is used to find type of the file,
whether it is directory, ascii text file etc.,
-b option suppresses file name.
"$i" $i gives file, if filename has spaces , it should be sorrounded by double quotes.
if condition checks for directory ,if not continue statement executed,i.e it goes to next item in the list,(skips below statements)
#!/usr/bin/bash echo "*************************************************************" echo "This example displays directory names in a current directory" echo "*************************************************************" for i in * do d=$(file -b "$i") if [ "$d" != "directory" ] then continue; fi; echo $i done
ADS