我目前正在尝试重命名一大组文件,并且一直使用相当笨拙的方法来执行此操作,例如:
rename 's:(.*)\.MOV:$1.mov:g' *.MOV
rename 's:(.*)\.JPG:$1.jpg:g' *.JPG
我真正想做的是能够使用以下命令组合所有这些命令'y'sed
运算符。显然,使用此运算符,您可以将项目转换为小写。问题是我只需要转换扩展名。有没有办法使用这个命令来做到这一点?我需要将以下表达式中的捕获组转换为小写:^.+\.(.+)$
。有没有办法做到这一点?我对这些转变有点陌生。
答案1
rename
从语法来看,这是 Debian、Ubuntu 及其衍生产品上基于 Perl 的版本。你不能使用tr
操作员因为它作用于整个弦。但是你可以匹配扩展名,并将其小写和\L
。
rename 's/\.[^.]*$/\L$&/' *.JPG *.MOV
这里是不必要的,但是如果正则表达式匹配的内容超过了您想要小写的部分,您可以将要匹配的部分放在团体:
rename 's/\.([^.]*)$/.\L$1/' *.JPG *.MOV
替换*.JPG *.MOV
为*.*
可对所有文件执行操作,无论扩展名如何。在 bash ≥4.3 中(以及在 bash 4.0–4.2 中,需要注意的是,这也会遍历目录的符号链接),您可以轻松地递归地对子目录中的文件等进行操作:
rename 's/\.[^.]*$/\L$&/' **/*.*
为了zsh 粉丝(:r
和:e
修饰语将扩展名与文件的其余部分隔离):
autoload zmv
zmv '*.(MOV|JPG)' '${f:r}.${(L)f:e}' # these extensions, current directory
zmv '*.*' '${f:r}.${(L)f:e}' # all extensions, current directory
zmv '**/*.*' '${f:r}.${(L)f:e}' # all extensions, recursive directory traversal