How can I make this code work?
#!/bin/bash
ARRAYNAME='FRUITS'
FRUITS=( APPLE BANANA ORANGE )
for FRUIT in ${!ARRAYNAME[@]}
do
echo ${FRUIT}
done
This code:
echo ${!ARRAYNAME[0]}
Prints APPLE. I'm tryng to do something similar but with "[@]" to iterate over the array.
Thanks in advance,
Despite the simple OP question, these answers won't scale for the most common, real use-cases, i.e., array elements containing whitespace or wildcards that should not yet be expanded to filenames.
This works:
Just as you should get in the habit of using
"$@"
not$@
, always quote inside( )
for array expansions, unless you want filename expansion or know there's no possibility of array elements containing whitespace.Do this:
X=("${Y[@]}")
Not this:
X=(${Y[@]})
${!ARRAYNAME[@]}
means "the indices ofARRAYNAME
". As stated in the bash man page sinceARRAYNAME
is set, but as a string, not an array, it returns0
.Here's a solution using
eval
.What you were originally trying to do was create an Indirect Reference. These were introduced in bash version 2 and were meant to largely replace the need for
eval
when trying to achieve reflection-like behavior in the shell.What you have to do when using indirect references with arrays is include the
[@]
in your guess at the variable name:All that said, it's one thing to use Indirect References in this trivial example, but, as indicated in the link provided by Dennis Williamson, you should be hesitant to use them in real-world scripts. They are all but guaranteed to make your code more confusing than necessary. Usually you can get the functionality you need with an Associative Array.
Here's a way to do it without eval.
See Bash trick #2 described here: http://mywiki.wooledge.org/BashFAQ/006
Seems to work in bash 3 and up.
Here's a more realistic example showing how to pass an array by reference to a function:
I just wanted to add another useful use-case. I was searching the web for a solution to a different, but related problem
eval
executes code containing array elements, even if they contain, for example, command substitutions. It also changes the array elements by interpreting bash metacharacters in them.A tool that avoids these problems is the
declare
reference, seeman bash
under declare: