Why this does not list anything? Thank you
FOLDER=()
ls /tmp/backup/ | while read DIR
do
FOLDER+=("$DIR")
done
echo ${FOLDER[1]}
Why this does not list anything? Thank you
FOLDER=()
ls /tmp/backup/ | while read DIR
do
FOLDER+=("$DIR")
done
echo ${FOLDER[1]}
Your example is designed to fail. For example:
ls
.Assuming that every entry in /tmp/backup is a directory, you can simply use shell globs to populate your array. If you may have files as well as directory entries, then you'll need to use find or use a shell test expression to ensure that the entry is actually a directory. For example:
# Enable special handling to prevent expansion to a
# literal '/tmp/backup/*' when no matches are found.
shopt -s nullglob
FOLDERS=(/tmp/backup/*)
for folder in "${FOLDERS[@]}"; do
[[ -d "$folder" ]] && echo "$folder"
done
# Unset shell option after use, if desired. Nullglob
# is unset by default.
shopt -u nullglob
To work around subshellissue (see Diego's answer), you can also do something like
while ....
done <<<$(ls)
while
gets executed in a child shell, and it cannot modify parent's variables, in this case, FOLDER
. You should try other ways. For example:
FOLDER=(`ls /tmp/backup`)
echo ${FOLDER[1]}
(will print the second file in there)
NOTE: Yes, I understand the problems of this solution, spaces, use of ls
, etc. I just wanted to point out the problem with while
. To complete the answer, yes, globbing should be used:
for dir in /tmp/backup/* ; do
test -d "$dir" && do_stuff_with_dir("$dir")
done
And, by not dying of purism, the usual (at least in UNIXes) is NOT having spaces in filenames. It is bad for your health :)
As the others already mentioned one of the problems with the code above is modifying of a variable in a subshell. The other is using +=
to populate the array. Unfortunately this just adds to zeroth element as a string, so that FOLDERS[1]
stays undefined.