在Linux中使用bash脚本查找并重命名多个文件。

问题描述 投票:0回答:1

举个例子,在一个目录中 /home/hel/files/ 一个应用程序把它的输出文件保存在那里,在文件名中带有特殊字符,我想在所有文件名中用下划线来代替这些特殊字符,例如,我写了一个bash脚本,简单地重复使用LinuxUnix的 "rename "命令来重命名文件。-:"<>@

我写了一个bash脚本,简单地重复使用LinuxUnix的 "rename "命令来重命名文件。

例如:文件名。rename.sh

#!/bin/bash
rename "s/\'/_/g" *
rename 's/[-:"<>@\,&\s\(\)\[\]?!–~%„“;│\´\’\+#]/_/g' *
rename 'y/A-Z/a-z/' *
rename 's/\.(?=[^.]*\.)/_/g' *
rename 's/[_]{2,}/_/g' *

我执行下面的find命令

find /home/hel/files/ -maxdepth 1 -type f -execdir /home/hel/scripts/rename.sh {} \+

现在的问题是:

这样做很好,除了事实上,它也会重命名子目录,如果它们的名字里有搜索的字符的话。

find命令只搜索文件而不是目录。

我尝试了一些其他的find变体,比如。

find /home/hel/files/ -maxdepth 1 -type f -execdir sh /home/hel/scripts/rename.sh {} \+
find /home/hel/files/ -maxdepth 1 -type f -execdir sh /home/hel/scripts/rename.sh {} +
find /home/hel/files/ -maxdepth 1 -type f -execdir sh /home/hel/scripts/rename.sh {} \;

它们都能用,但结果都一样。

不起作用的是什么。

find /home/hel/files/ -maxdepth 1 -type f -exec sh /home/hel/scripts/rename.sh {} \+

这是很危险的, 因为它会重命名当前目录下的目录和文件, 你也会调用find命令.

也许有人知道为什么会这样,或者有更好的解决办法。

bash file-rename batch-rename
1个回答
0
投票

脚本 rename.sh 完全没有使用它的命令行参数,而是使用 glob 的方式自己搜索文件和目录(!)。*.

将你的脚本修改为以下内容。

#!/bin/bash
rename -d s/\''/_/g;
s/[-:"<>@\,&\s\(\)\[\]?!–~%„“;│\´\’\+#]/_/g;
y/A-Z/a-z/;
s/\.(?=[^.]*\.)/_/g;
s/[_]{2,}/_/g' "$@"

然后使用 find ... -maxdepth 1 -type f -exec sh .../rename.sh {} +.

变化

  • 使用 "$@" 而不是 * 来处理作为参数的文件,而不是当前目录中的所有文件。
  • 执行 rename 二次 rename 找不到用 "$@" 在被第1次改名后 rename.
  • 使用 -d 选项,这样就只修改了基名。find 总是在文件前面放一个路径,至少是在 ./. 如果没有这个选项 rename 会变 ./filenamemangledPath/newFilename 并因此将该文件移至另一目录。

请注意 man rename 有失偏颇

--path, --fullpath
        Rename full path: including any directory component.  DEFAULT

-d, --filename, --nopath, --nofullpath
        Do not rename directory: only rename filename component of path.

对于一个给定的路径 rename -d 's...' some/path/basename 只是处理 basename 而忽略了前面的部分 some/path/. 如果 basename 是一个目录,它仍然会被重命名,尽管有 -d 选项。

© www.soinside.com 2019 - 2024. All rights reserved.