Renaming files in linux with a regex
Solution 1:
I used to write perl scripts to do this, until I discovered the rename command.
It accepts a perl regex to do the rename:
for this, I just typed two commands:
rename 's/(\w+)-(\w+)-(\d\d)-(\d{4})-NODATA.txt\$1.$4$3$2.log$//' *
rename 'y/A-Z/a-z/' *.log
For some distros though, rename
doesn't have this functionality (see its man page), and you may have to install perl-rename
or prename
.
Solution 2:
mmv is a standard linux utility to move/rename multiple files. It is available from the repos for most distributions. For your example above, you could do:
mmv '*-Log-*-*-*-NODATA.txt' '#l1.#4#3#2.log'
For more information, read this debaday article or the man page.
Solution 3:
Since i don't have a rename command, i am relying on this:
for myfile in /my/folder/*; do
target=$(echo $myfile|sed -e 's/foo/bar/g')
mv "$myfile" "$target"
done
Solution 4:
rename
util is not very "standard". Each distro ships with a different rename
tool. For instance, here on Gentoo, rename
is from sys-apps/util-linux
package and does not support regex.
Hamish Downer suggested mmv
, it seems useful, specially for use inside scripts.
On the other hand, for the general case, you might want renameutils. It has qmv
and qcp
commands, which will open a text editor of your choice (my preference: Vim) and allow you to edit the destination filenames there. After saving and closing the editor, qmv
/qcp
will do all the renaming.
Both mmv
and qmv
are smart enough to rename files in correct order and also to detect circular renames, and will automatically make a temporary file if needed.