Is there any way to apply Bash variable substitution on find
's output? I know I've seen someone do it on Stack Overflow but I can't seem to find that particular post anymore.
As an example, let's say I want to rename files ending in *.png
to *_copy.png
. I know I can do this using rename
but it's just a thought experiment.
Now I'd like to be able to do something like this:
find . -name "*png" -exec mv "{}" "${{}%.*}_copy.png" \;
Which results in an invalid substitution. Of course, I could first assign the output to a variable and then apply substitution in a sub-shell, but is this really the only way?
find . -name "*.png" -exec bash -c 'var="{}"; mv "{}" "${var%.*}_copy.png"' \;
Or is there any way this can be achieved directly from {}
?
Consensus
As Etan Reisner remarked, a better and safer way to handle the output of find
would be to pass it as a positional argument:
find . -name "*.png" -exec bash -c 'mv "$0" "${0%.*}_copy.png"' "{}" \;
It took me a while to get the question. Basically you are asking if something like:
echo "${test.png%.png}"
could be used to get the word test
.
The answer is no. The string manipulation operators starting with ${
are a subset of the parameter substitution operators. They work only on variables, not with string literals, meaning you need to store the string in a variable before. Like this:
img="test.png"
echo "${img%.png}"
Just for travellers from Google, I would use rename
for this particular task. (As the OP already mentioned in his question). The command could look like this:
find -name '*png' -execdir rename 's/\.png/_copy.png/' {} +
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