Executing a script in multiple subdirectories simultaneously
Hi,
I'm a newbie to shell scripting and have come up with a script (named "drop_3rd.sh") that I'd like to execute in several subdirectories that all have the same name, but I don't want to have to change into each subdirectory (there are hundreds) to execute the script. All the subdirectories have the same name ("final_alignments"), but are located in parent directories with different names. All these parent directories are in the same "super parent" directory. I've tried to do this using "for/do" and "find" but no luck so far. Please help, as I'm sure this is a straightforward problem that can easily be solved by someone with more experience. Thanks! |
I believe you're on the right track using `find` and a for/do loop. It'd be a good idea to show us what is the exact code you're currently using so that we might point out what you're doing wrong. Anyhow, here's the basic idea I'd use:
Code:
for location in $(find /path/to/super_parent_directory -type d -name "final_alignments"); do If this doesn't work, please show us (copy & paste) from your terminal how you've used this code, and what the results and error messages are. Good luck! |
Let find do it all
Find can locate the directories, cd to each one, and run a command like this.
find /path/to/super_parent_directory -type d -name "final_alignments" -execdir /path/to/script \; The \; is important as it keeps the shell from interpreting it and passes it on to the find command. |
@ danny,
thanks, that's something I hadn't thought of! |
Thanks!
Both these solutions seem to work, but I went with Danny's to save some time.
Thanks! :) |
You choosed the right one, because the first don't work if there is spaces on dir names.
|
FYI
The reason is that the results of the find command are "expanded" and placed on the "for" command line before each iteration, so the spaces get parsed as separate words. Another overhead problem is that the "( command )" has to create a subshell environment for each line. The "find" version is best. Here is a way you could do it if you'd like. find /path/to/super_parent_directory -type d -name "final_alignments" | while read location; do pushd "$location">/dev/null; /path/to/script; popd>/dev/null; done; In this example spaces in directory names get passed on OK. You always have to be careful of spaces in shell scripts. I always enclose variables being expanded in double quotes so it is expanded as one "word". The pushd and popd commands provide for cd'ing to a directory then poping back without having to start a subshell. |
OK, you already have a solution, but anyway.
What about: Code:
for dir in /path_to/super_parent/*/final_alignment; do |
You can also get around the word splitting by using a while loop instead:
Code:
while read -r line |
All times are GMT -5. The time now is 03:17 PM. |