0

I am trying to write a function to input info about different people, for instance, five students. I intend to do it using for loop and without declaring an array.

function student() {
    for (( i = 0; i < 5; i++ )); do
        echo "Name"
        read name$i
    done
   }  

I believe that at every iteration it would be a different variable name$i the input is read for. Now when I try to display the same data using a for loop

function student() {
    for (( i=0;i < 5; i++)); do
    echo $(name$i)
    done
}

it shows an error name0: command not found

Now when I display the values explicitly like echo "$name0" echo "$name1", it all works fine which tells me that the variables are all declared and input is populated. The problem is that I may not be accessing the variable names right while trying to display the values because when I write echo "$name$i", the output is name0. It means that it takes "name" as a string and the values of i. I have tried to concatenate the string "name" with values of "i" using a couple of ways. There is a way to bind both like namen="${i}name" but I want the integer values after the string so it didn't work for me. I am new to shell scripting, so all your worthy suggestions would be helpful.

Muhammad Arslan
  • 380
  • 1
  • 4
  • 10
  • 2
    Is there any reason you're not using an array for this (i.e. `name[0]`, `name[1]`, etc)? In any case, I recommend running your script through [shellcheck.net](https://www.shellcheck.net) and fixing what it points out. – Gordon Davisson Oct 11 '22 at 21:36
  • 1
    The expression `$(p)` runs a the program `p` and interpolates its stdout. Hence `$(name$i)` tries to run a program named `name0`. Since there is no executable of this name in your PATH, you get the error message. If you don't want to use an array, you can use a _nameref_ instead. See the bash man-page, section _PARAMETERS_. – user1934428 Oct 12 '22 at 07:13

1 Answers1

2

Setup:

$ name0=0; name1=1; name2=2; name3=x; name4=y

Running a web search on bash dynamic variables should provide a good number of options, among them:

indirect reference

student() {
for ((i=0; i<5; i++))
do
    x="name${i}"
    echo "${!x}"
done
}

nameref

student() {
for ((i=0; i<5; i++))
do
    declare -n x="name${i}"
    echo "${x}"
done
}

Both of these generate:

$ student
0
1
2
x
y
markp-fuso
  • 28,790
  • 4
  • 16
  • 36