1

I have a set of 100 questions. My requirement is when a user enter "yes", then question 1 should appear. If not, directly it go to question 2. Like that it should go on till 100 questions. Any lead would be appreciated.

This is what I tried, but it is failing.

#!/bin/bash echo "Execute question1 " select result in Yes No do echo "How to see apache config file" exit done echo "execute question2" select result in Yes No Cancel do echo "Command for listing processes" exit done 

Thanks in advance

4
  • Can you elaborate your question? Is it always has to show question 1 on "Yes"? or it is like, it should iterate from 1 to 100 and in case user enters Yes, it should print that particular question or else it should just move to next question? Commented May 24, 2021 at 6:04
  • That's right. If the user enter yes for question1, it should print that question and move to next. If he enters NO for question 1, it should directly go for question2 Commented May 24, 2021 at 6:07
  • Also, where are you maintaining the list of 100 questions? Commented May 24, 2021 at 6:08
  • Planned to write it on the script itself. Sorry I am new to this. Is there any better way? Commented May 24, 2021 at 6:11

3 Answers 3

3

Here is a way to do this with an array.

#!/bin/bash questions=( "How to see apache config file" "Command for listing processes" "My hovercraft is full of eels" ) for((q=0; q<${#questions[@]}; q++)); do echo "Execute question $q?" select result in Yes No; do case $result in Yes) echo "${questions[q]}";; esac break done done 

Using select for this seems rather clumsy, though. Perhaps just replace it with

 read -p "Execute question $q? " -r result case $result in [Yy]*) echo "${questions[q]}";; esac 

Having just a list of questions still seems weird. With Bash 5+ you could have an associative array, or you could have a parallel array with the same indices with answers to the questions. But keeping each question and answer pair together in the source would make the most sense. Maybe loop over questions and answers and assign every other one to an answers array, and only increment the index when you have read a pair?

pairs=( "How to see Apache config file" "cat /etc/httpd.conf" "Command for listing processes" "ps" "My hovercraft is full of what?" "eels" ) questions=() answers=() for((i=0; i<=${#pairs[@]}/2; ++i)); do questions+=("${pairs[i*2]}") answers+=("${pairs[1+i*2]}") done 

This ends up with two copies of everything, so if you are really strapped for memory, maybe refactor to just a for loop over the strings and get rid of the pairs array which is only useful during initialization.

Sign up to request clarification or add additional context in comments.

Comments

1

Use an array of questions and loop over it, like this:

#!/bin/bash n=1 questions=( 'How to see apache config file' 'Command for listing processes' ) check_user_input(){ read -p "y/n " input case $input in [Yy]*) return 0;; [Nn]*) return 1;; *) check_user_input;; esac } for question in "${questions[@]}"; { echo "Execute question $n" check_user_input && echo "$question" ((n++)) } 

Comments

0

Here is a straight forward example. Play with it.

#!/bin/bash echo "Type 'y' for yes, 'n' to skip or 'q' to quit and press Enter!" for((i=1; i < 101; ++i)); do echo 'Execute question '$i while read user_input; do if [[ "$user_input" = 'q' ]]; then break 2 elif [[ "$user_input" = 'n' ]]; then break elif [[ $i -eq 1 ]]; then echo 'How to see apache config file?' break 2 # Change from "break 2" to "break" for the next question. elif [[ $i -eq 2 ]]; then echo 'Command for listing processes.' break 2 # Change from "break 2" to "break" for the next question. else echo "Wrong input: $user_input" echo "Type 'y' for yes, 'n' to skip or 'q' to quit and press Enter!" fi done done echo 'Finished' 

2 Comments

The big if / elif / elif ... statement looks like it wants to be desperately refactored into a case statement.
@triplee Hahha.. Yes. I'm just making it straight forward here. OP probably want to use break instead of break 2 for the last 2 elif's to progress though. I'll leave it as an execise for the OP.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.