从所有文件名中删除撇号

从所有文件名中删除撇号

我尝试从目录中的所有文件名中删除撇号。

for i in *; do mv $i `echo $i | tr -d "'"`; done

执行此命令后,没有任何内容被重命名。

你知道这里出了什么问题吗?

答案1

你可以尝试这样的事情(bash):

shopt -s nullglob
for i in *\'* ; do mv -v "$i" "${i/\'/}" ; done

这使用 shell 字符串替换。您可能不想使用'其中不包含的文件,因为这样mv会失败。如果没有该选项,如果没有匹配的文件,nullglob则将传递 glob 模式本身。mv

答案2

$foo始终在变量替换和命令替换两边加上双引号$(foo)(除非您知道为什么需要将它们排除在外以及为什么可以这样做)。

for i in *; do mv "$i" "$(echo "$i" | tr -d "'")"; done

这基本上可以工作,但有一些限制:

  • 如果文件名以 开头-,您将得到不良行为或错误,因为mv会将其解释为选项。
  • 这不会影响名称以..
  • 对于某些设置,这会破坏echo命令中的反斜杠。
  • 名称末尾的换行符会丢失。

在 ksh93、bash 和 zsh 中,您可以使用该构造轻松编写此代码${VARIABLE//PATTERN/REPLACEMENT}。添加--mv会处理以-.如果您的文件名以 开头.,请根据需要在后面添加.*或。.[^.]* ..?**

for i in *; do mv -- "$i" "${i//\'/}"; done

在 zsh 中,您可以使用zmv:

zmv '(*)' "\${1//\\'/}"

在 Debian、Ubuntu 和其他衍生版本下,您可以使用renamePerl 脚本。

rename "s/'//g" *

答案3

我认为您的问题是该文件的名称中也有空格。没有它我无法重现你的错误。

$ touch "file" "user's file"
$ for i in *; do mv $i `echo $i | tr -d "'"`; done
mv: `file1' and `file1' are the same file
mv: target `file' is not a directory

所以它失败的原因是第二条消息:target 'file' is not a directory

当您的 for 循环看到带有空格的文件时,它会运行以下命令:

mv user's file users file

因此它认为您指定了三个文件(user'sfileusers),以及一个将这些文件移动到的目录(file)。

正确引用两者应该可以解决您眼前的问题

$ for i in ./*; do mv "$i" "$(echo "$i" | tr -d "'")"; done

相关内容