类unix系统上如何快速批量重命名文件


=Start=

缘由:

中文环境的macOS系统上自动生成的一些文件有不少文件名是包含空格的,对于终端操作不是太方便,所以需要将文件名中的空格批量替换成下划线方便后面的处理。

另外就是不得不感概一下——大模型可能是你能快速直接接触到的最博学的朋友了如果是现实已有解决方法的话,你只要通过合适的prompt提示词向他提问,他大概率是能帮你找到一些方法或思路的,所以你要利用好这个工具去扩展自己的能力圈,但在过去,那些内容你过去如果没有实际做过,你是很难想到的(常规的搜索引擎能检索到的内容和效果也非常有限)。

正文:

参考解答:

对当前目录和子目录下的文件进行处理

# vim ~/.zshrc
rename1() {
for file in *' '*; do [ -f "$file" ] && mv "$file" "${file// /_}"; done
}

rename22() {
find . -depth -name '* *' -execdir bash -c 'for f; do mv "$f" "${f// /_}"; done' bash {} +
# 匹配文件名中有空格的文件列表,然后对其中的每一项执行后面指定的命令
}

# source ~/.zshrc

# 对当前目录下文件名包含空格的文件进行重命名,对文件名中的空格用下划线进行替换。使用的时候要切换到对应目录下执行该命令。
rename1

对当前目录及其子目录下的文件进行处理(测试OK)

rename22() {
find . -depth -name '* *' -execdir bash -c 'for f; do mv "$f" "${f// /_}"; done' bash {} +
# 匹配文件名中有空格的文件列表,然后对其中的每一项执行后面指定的命令
}


#借助find命令的选项控制进入子目录的深度
find . -iname '* *'.png -maxdepth 1 -type f -print0 | while IFS= read -r -d $'\0' fp; do
    mv "$fp" "${fp// /_}"

    #上面1行内容效果等价于下面的这些除了echo打印功能之外的内容
    echo "$fp"

    newname=$(echo "$fp" | tr ' ' '_')
    echo "$newname"
    # 上面2行也可以用下面这一行来替换
    echo "${fp// /_}"

    # mv "$fp" "$newname"
done
$ man find
...
-execdir utility [argument ...] ;
    The -execdir primary is identical to the -exec primary with the exception that utility will be executed from the directory that holds the current file.  The filename substituted for the string “{}” is not qualified.
    -execdir primary与-exec primary相同,不同之处在于实用程序将从保存当前文件的目录执行。这里(以英文分号结尾)不支持替换字符串“{}”的文件名。

-execdir utility [argument ...] {} +
    Same as -execdir, except that “{}” is replaced with as many pathnames as possible for each invocation of utility.  This behaviour is similar to that of xargs(1).  The primary always returns true; if at least one invocation of utility returns a non-zero exit status, find will return a non-zero exit status.
    与-execdir相同,除了每次调用实用程序时“{}”被替换为尽可能多的路径名。这种行为类似于xargs(1)。初级函数总是返回true;如果至少有一次调用utility返回非零退出状态,find将返回非零退出状态。
...
参考链接:

通义千问
https://tongyi.aliyun.com/qianwen/

=END=


发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注