Fry
Fry

Reputation: 6275

Declare array with result of find command

I would like put the result of command find *.txt in array and then iterate over the array like this

for file in array
do

done

I need to put in array because later I need to access to the array. So the solution

for file in `find *.txt`
do

done

isn't good for me.

Upvotes: 0

Views: 95

Answers (4)

John1024
John1024

Reputation: 113934

The other answers all have virtues. As a complement to them, here is an approach which (a) is safe on even the most difficult file names, (b) allows the full use of the power of find, and (c) avoids eval:

array=()
while read -r -d $'\0'; do
    array+=("$REPLY")
done < <(find . -name '*.txt' -print0)

Upvotes: 0

Barmar
Barmar

Reputation: 782130

Use array assignment syntax:

array=($(find *.txt))

If there can be spaces in the filenames, you should put

IFS=$"\n"

before the above command. If there can be newlines in the filenames, it gets really complicated and I'm not sure of a good way to handle it.

Then you can iterate over it with:

for file in "${array[@]}"

Upvotes: 1

gniourf_gniourf
gniourf_gniourf

Reputation: 46883

If you're sure that you don't have any newlines in your filenames, mapfile is a good choice:

mapfile -t array < <(find . -name '*.txt')

Now if you want something more bullet proof, you can use:

mapfile -t array < <(find . -name '*.txt' -exec bash -c 'printf "%q\n" "${@:0}"' {} +)
eval array=( ${array[@]} )

You should feel really bad when seeing this last line: eval and unquoted ${array[@]}. It works and it's bullet proof since the array array has been built using the '%q' modifier of printf, so everything is nicely escaped or quoted so as to be used safely here!

Upvotes: 1

chepner
chepner

Reputation: 532053

If you are using bash 4, and as you don't appear to be using any other feature of find except its ability to recurse through subdirectories, I suggest using the globstar option instead.

shopt -s globstar
array=( **/*.txt )

This avoids spawning an external process in which to run find, as well as avoiding any nasty surprises if any of the matching files have whitespace in their names.

Upvotes: 1

Related Questions