I'm sure I'm missing something but I can't figure it out. Given:
$ find -type f
./hello.txt
./wow.txt
./yay.txt
how come the next two commands render different results?
$ find -type f -exec basename {} \;
hello.txt
wow.txt
yay.txt
$ find -type f -exec echo $(basename {}) \;
./hello.txt
./wow.txt
./yay.txt
$(basename {}) is evaluated before the command runs.
The result is {} so the command echo $(basename {}) becomes echo {} and basename is not run for each file.
A quick debug on that using the bash -x debugger demonstrated this,
[The example is my own, just for demonstration purposes]
bash -xc 'find -type f -name "*.sh" -exec echo $(basename {}) \;'
++ basename '{}'
+ find -type f -name '*.sh' -exec echo '{}' ';'
./1.sh
./abcd/another_file_1_not_ok.sh
./abcd/another_file_2_not_ok.sh
./abcd/another_file_3_not_ok.sh
And for just basename {}
bash -xc 'find -type f -name "*.sh" -exec basename {} \;'
+ find -type f -name '*.sh' -exec basename '{}' ';'
1.sh
another_file_1_not_ok.sh
another_file_2_not_ok.sh
another_file_3_not_ok.sh
As you can see in the first example, echo $(basename {}) gets resolved in two steps, basename {} is nothing but the basename on the actual file (which outputs the plain file name) which is then interpreted as echo {}. So it is nothing but mimic-ing the exact behaviour when you use find with exec and echo the files as
bash -xc 'find -type f -name "*.sh" -exec echo {} \;'
+ find -type f -name '*.sh' -exec echo '{}' ';'
./1.sh
./abcd/another_file_1_not_ok.sh
./abcd/another_file_2_not_ok.sh
./abcd/another_file_3_not_ok.sh
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With