如何通过替换文件名中的单词来重命名多个文件?


36

将ACDC替换为AC-DC

例如我们有这些文件

ACDC-摇滚乐不受噪音污染.xxx

ACDC-Rocker.xxx

ACDC-Shoot To Thrill.xxx

我希望他们成为:

AC-DC-摇滚乐不受噪音污染.xxx

AC-DC-Rocker.xxx

AC-DC-Shoot To Thrill.xxx

我知道sed或awk用于此操作。我无法在Google上搜索任何内容,因此我正在寻求您的帮助=)您能否为此任务提供完整的有效Shell命令?

反馈:OSX用户的解决方案


1
我觉得这里还有一个更大的问题-您是否正在尝试修复mp3文件名?多年来,人们为此编写了许多脚本。我想我曾经使用过一个mp3fixer
Phil Hollenback

不,这不是关于MP3的我只是要管理具有类似名称的一些巨大的文件,所以我需要重命名所有的人这个漂亮的解决方案的一切东西必须更换或固定...常见的情况
霍尔姆斯

Answers:


45
rename 's/ACDC/AC-DC/' *.xxx

man rename

DESCRIPTION
       "rename" renames the filenames supplied according to the rule specified as the 
first argument.  The perlexpr argument is a Perl expression which is expected to modify the 
$_ string in Perl for at least some of the filenames specified.  If a given filename is not 
modified by the expression, it will not be renamed.  If no filenames are given on
           the command line, filenames will be read via standard input.

例如,要重命名所有匹配“ * .bak”的文件以去除扩展名,您可能会说

rename 's/\.bak$//' *.bak

要将大写名称转换为小写,您可以使用

rename 'y/A-Z/a-z/' *

5
请注意,许多linux机器都从util-linux附带了重命名,它实现了简单的替换,而不是正则表达式。因此,如果重命名在没有做任何事情的情况下静默失败,则可能是使用了错误的rename
Phil Hollenback

我一直在寻找这个!谢谢!
霍尔姆斯2011年

@PhilHollenback然后如何找到/安装正确的一个?:)
亨利

当文件名中带有下划线而不是空格时,它不起作用-我该如何解决?
unfa

13

该答案包含所有其他答案的重要内容,而忽略了诸如的异端ls | while read

当前目录:

for file in ACDC*.xxx; do
    mv "$file" "${file//ACDC/AC-DC}"
done

包括子目录:

find . -type f -name "ACDC*" -print0 | while read -r -d '' file; do
    mv "$file" "${file//ACDC/AC-DC}"
done

换行符实际上不太可能出现在文件名中,因此在使用包含空格的名称时,这可能会更简单:

find . -type f -name "ACDC*" | while read -r file; do
    mv "$file" "${file//ACDC/AC-DC}"
done

9

要使用renamePhil提到的util-linux版本(在Ubuntu上称为rename.ul):

rename ACDC AC-DC ACDC*

要么

rename.ul ACDC AC-DC ACDC*

1
您的变体是最好的=)谷歌上有这么多关于查找,发送和awk的愚蠢文章...到这个简单的操作,已经为namedutils egxist提供了!
霍尔姆斯2011年

4

使用bash外壳

find . -type f -name "ACDC*" -print0 | while read -d $'\0' f
do
   new=`echo "$f" | sed -e "s/ACDC/AC-DC/"`
   mv "$f" "$new"
done

注意:using find将处理当前目录及其下的目录。


1

取决于您的外壳。在zsh中,我会这样做:

for file in ACDC*.xxx; do
    mv "$file" "$(echo $file | sed -e 's/ACDC/AC-DC/')"
done

可能不是最好的解决方案,但可行。


1

使用bash:

ls *.xxx | while read fn; do
    mv "${fn}" "${fn/ACDC/AC-DC}";
done

如果您已rename安装程序:

rename 's/ACDC/AC-DC/' *.xxx
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.