Reputation: 331
I've found several answers that look like they should work, but when I run a script to try and remove dots from directory names, the dots seem to confuse the script regardless of quoting. For instance, I have tried this on a directory named s. om. e dir (25)
:
for dir in $(find . -type d -maxdepth 1 -name *.*); do
mv "$dir" `echo "$dir" | tr '.' '_'`
done
and get this output in the terminal:
mv: rename ./s. to _/s_: No such file or directory
mv: rename om. to om_: No such file or directory
mv: rename e to e: No such file or directory
mv: rename dir to dir: No such file or directory
mv: rename (25) to (25): No such file or directory
How can I rename the directory from s. om. e dir (25)
to s_ om_ e dir (25)
without the code breaking at each instance of a dot?
Upvotes: 2
Views: 1472
Reputation: 785781
Instead of echo | tr
, you can simply use parameter substitution:
mv -- "$dir" "${dir//./_}"
You should use a while
loop instead of a for
loop in a process substitution:
while IFS= read -r -d '' dir; do
mv -- "$dir" "${dir//./_}"
done < <(find . -type d -maxdepth 1 -name '*.*' -print0)
You should also quote your file pattern in find
.
Moreover, since you're only iterating directories in the current directory, you can use this glob
:
for dir in *.*/; do
mv -- "$dir" "${dir//./_}"
done
Upvotes: 3
Reputation: 85867
The problem is using for
/in
on the output of find
.
If you have the Perl version of rename
, you can simply do
rename 'tr/./_/' *.*/
Otherwise,
for i in *.*; do
[ -d "$i" ] || continue
mv -- "$i" "${i//./_}"
done
should work.
Upvotes: 4