There are a couple of ways to solve this, depending on whether you need to worry about files with spaces or other special characters in their names.
If none of the filenames have spaces or special characters (they consist only of letters, numbers, dashes, and underscores), then the following is a simple solution that will work. You can use $(command)
to execute a command, and substitute the results into the arguments of another command. The shell will split the result on spaces, tabs, or newlines, and for
assign each value to $f
in turn, and run the command on each value.
for f in $(find . -name myFile)
do
cp something $f
done
If you do have spaces or tabs, you could use find's -exec
option. You pass -exec command args
, putting {}
where you want the filename to be substituted, and ending the arguments with a ;
. You need to quote the {}
and ;
so that the shell doesn't interpret them.
find . -name myFile -exec cp something "{}" \;
Sometimes -exec
is not sufficient. For example, in this question, they wanted to use Bash parameter expansion to compute the filename. In order to do that, you need to pass -exec bash -c 'your command'
, but then you will run into quoting problems with the {}
substitution. To solve this, you can use -print0
from find
to print the results delimited with null characters (which are invalid in filenames), and pipe it to a while read
loop that splits parameters on nulls:
find . -name myFile -print0 | (while read -d $'\0' f; do
cp something "$f"
done)