Shell Script - Loops

melanie17

New Member
Joined
Dec 21, 2021
Messages
4
Reaction score
2
Credits
36
Hello Together

I am new here, as well as on Linux or Ubuntu.

Need to write a useful shell script that does something useful as an exercise.

For this I have decided on a small program that helps you choose a restaurant. For this, of course, you need to know what you like to eat.

The task says that you have to use statements and loops.
I have already used statements, but I don't know what kind of useful loop I could use? Do you have any ideas, or what else could I program? I don't know much about loops!
I thought that in the main program I could use a while loop to adjust the time instead of If.

See the "code section"
Code:
###################### Main Program #######################
if [ $HOUR -gt 11 ] && [ $HOUR -lt 14 ]; then
        echo "Time for lunch: "
        choosefood

else
        if [ $HOUR -gt 17 ] && [ $HOUR -lt 21 ]; then

                echo "Time for dinner: "
                choosefood


        else
                echo "It isn't time o eat!!"
        fi
fi

#################### End Main Program #####################
 


Hello Together

I am new here, as well as on Linux or Ubuntu.

Need to write a useful shell script that does something useful as an exercise.

For this I have decided on a small program that helps you choose a restaurant. For this, of course, you need to know what you like to eat.

The task says that you have to use statements and loops.
I have already used statements, but I don't know what kind of useful loop I could use? Do you have any ideas, or what else could I program? I don't know much about loops!
I thought that in the main program I could use a while loop to adjust the time instead of If.

See the "code section"
Code:
###################### Main Program #######################
if [ $HOUR -gt 11 ] && [ $HOUR -lt 14 ]; then
        echo "Time for lunch: "
        choosefood

else
        if [ $HOUR -gt 17 ] && [ $HOUR -lt 21 ]; then

                echo "Time for dinner: "
                choosefood


        else
                echo "It isn't time o eat!!"
        fi
fi

#################### End Main Program #####################
Looking at your code - I don't think a while loop would be handy here.

What does your choosefood function do?
If it asks the user for some kind of input, you could use a while loop to validate the users input. So the loop will keep re-iterating until the user enters some valid input.
 
G'day @melanie17 and welcome to linux.org :)

This sounds like a homework or assignment exercise, is that the case? We don't do homework, because then you don't learn well enough.

Have you asked your teacher, tutor or professor for clarification, and what have you Googled so far?

If Jas is happy enough to continue, I will leave that to his choice.

Cheers

Chris Turner
wizardfromoz
 
okay!
Looking at your code - I don't think a while loop would be handy here.

What does your choosefood function do?
If it asks the user for some kind of input, you could use a while loop to validate the users input. So the loop will keep re-iterating until the user enters some valid input.
he has a statement when it is time to eat (noon: 11-14 o'clock, evening: 17-21 o'clock)
during this time you can choose what you want (asian, fast food or veggie)
and a random generator spits out the restaurant (stored in array)

the other part of the code looks like this:
Code:
#!/bin/bash

################Define variables######################
HOUR=`date +%H`
#oder HOUR=`date | awk '{ print $4 }' | cut -c 1-2`

#Asia Food
Array1=("Mooch" "Oishii" "Yoojis" "Cha Cha" "Mishio" "Rice Up!")

#American Food (fast food)
Array2=("Burger King" "Mac Donalds" "Subway" "KFC" "Five Guys")

#Veggie Food (because Veggie is life!!)
Array3=("Tibits" "Hiltl" "Roots" "Beans & Nuts")



#####################Create function that randomly selects the restaurant#####################
choosefood()
{
echo -e "---Selection---\nAsia [1] \nAmerican [2] \nVeggie [3] \n"
echo -e "Which kitchen do you like? \nInput: "
read FOOD-TYPE


re='^[1-3]+$'
if ! [[ $FOODTYPE =~ $re ]] ; then
        echo "Error: The entered number does not correspond to the specified selection!"
fi


#Asia Food
if [ $FOODTYPE == 1 ]; then
        #Random Select Asia restaurant
        echo "The magic mussel has chosen: ${Array1[RANDOM%4]}"

fi

#Fast Food
if [ $FOODTYPE == 2 ]; then
        #Random Select Fast Food restaurant
        echo "The magic mussel has chosen: ${Array2[RANDOM%3]}"
fi

#Veggie
if [ $FOODTYPE == 3 ]; then
        #Random Select Veggie restaurant
        echo "The magic mussel has chosen:  ${Array3[RANDOM%4]}"
fi
}
 
G'day @melanie17 and welcome to linux.org :)

This sounds like a homework or assignment exercise, is that the case? We don't do homework, because then you don't learn well enough.

Have you asked your teacher, tutor or professor for clarification, and what have you Googled so far?

If Jas is happy enough to continue, I will leave that to his choice.

Cheers

Chris Turner
wizardfromoz
Hi Chris,

thanks for the welcome!

I know you guys don't do the homework... I was just asking for input and if it is possible to use a loop instead of an if-statement.
I have already written the code!
 
Good luck, you are in good hands with Jas. :)
 
@melanie17 - In that case, you could use a while loop in the code where you get the selection from the user, in order to validate the users selection and repeat the question if they fail to enter something valid.

So your choosefood() function could look something like this:
Bash:
choosefood()
{
echo -e "---Selection---\nAsian [1] \nAmerican [2] \nVeggie [3] \n"
re='^[1-3]+$'
while true # loop infinitely, until the user enters something valid
do
    read -n1 -p "Which type of food would you like? (1..3) : " FOODTYPE

    if ! [[ $FOODTYPE =~ $re ]] ; then
        echo -e "\nError: Invalid selection, enter a number between 1 and 3!"
    else # user entered something valid
        break; # so break out of the loop
    fi
done

echo -e "\nThe magic mussel has chosen: "

if [ "$FOODTYPE" == "1" ]; then
        #Select random Asian restaurant
        echo "${Array1[RANDOM%4]}"
elif [ "$FOODTYPE" == "2" ]; then
        #Select random Fast Food restaurant
        echo "${Array2[RANDOM%3]}"
elif [ "$FOODTYPE" == "3" ]; then
        #Select random Veggie restaurant
        echo "${Array3[RANDOM%4]}"
fi
}

Notes on the above:
1. Uses an infinite while loop to validate the users input.
The user will be prompted until they enter something valid.

2. Uses the read command to read a single character from the buffer - so all the user has to do is press a single key, no need to press enter.
If the user selects a number between 1 and 3, we break out of the loop and the final part of the function chooses a random restaurant. If the user presses any other key, they see an error message, the loop re-iterates and they are asked the question again.
Also note, the read command includes the prompt, no need for an extra echo with the prompt before the read. It's easier to include the prompt with the read command.

3. I've factored out the repeated "The magic mussel has chosen: " string to appear just before the random restaurant selection happens.
Rather than typing it 4 times, it was just lazier for me to write it the once! Ha ha!

4. Because your final set of if..fi statements are all related, I've used an if..elif.. style if statement instead, to group them all together.

Those statements could also be refactored into a case statement, like this:
Bash:
echo -e "\nThe magic mussel has chosen: "

case "$FOODTYPE" in
    1) #Select random Asian restaurant
        echo "${Array1[RANDOM%4]}"
        ;;
    2)  #Select random Fast Food restaurant
        echo "${Array2[RANDOM%3]}"
        ;;
    3)  #Select random Veggie restaurant
        echo "${Array3[RANDOM%4]}"
        ;;
esac

Both do the same thing. Personally, I think the case statement looks nicer and shows the purpose of the code more clearly/succinctly.
But as you only have three options, there is nothing wrong with using if..elif statements. But if you were dealing with a lot of options, then a case statement would almost certainly be better.

Also, regarding your main program:
Bash:
###################### Main Program #######################
if [ $HOUR -gt 11 ] && [ $HOUR -lt 14 ]; then
        echo "Time for lunch: "
        choosefood

else
        if [ $HOUR -gt 17 ] && [ $HOUR -lt 21 ]; then

                echo "Time for dinner: "
                choosefood


        else
                echo "It isn't time to eat!!"
        fi
fi

#################### End Main Program #####################

This is another place where the logic would be much clearer if you used if..elif..else
Like this:
Bash:
if [ $HOUR -gt 11 ] && [ $HOUR -lt 14 ]; then
    echo "Time for lunch: "
    choosefood
elif [ $HOUR -gt 17 ] && [ $HOUR -lt 21 ]; then
    echo "Time for dinner: "
    choosefood
else
    echo "It isn't time to eat!!"
fi
The if..elif..else.. style syntax is a little more compact and succinct than what you were doing before.
All of the related conditions fall under a single if..fi.. block, with any additional conditional clauses in elif statements and the final/fallback clause in an else statement.

I hope this has helped.
Best regards!
 
Thank you for the detailed explanation @JasKinasis
Very interesting and clear how you can write the code in different ways. Could learn a lot from your help, am very grateful!

Definitely very helpful!
Best regards
 

Members online


Top