如何使用脚本或 Bash 命令根据模式删除重复文件(参见下面的示例)

如何使用脚本或 Bash 命令根据模式删除重复文件(参见下面的示例)

我的问题很简单:

我有以下命名的视频文件:

  • xxxx_yyy_720_3800.mp4
  • xxxx_yyy_720_8000.mp4

其中 yyy 的长度可以变化(例如 yyyyyy 或更多 y)

由于我不习惯使用 shell 脚本,所以我想自动删除(在指定的文件夹中)

  • xxx_yyy_720_3800.mp4如果存在同名文件,并且如果文件xxx_yyy_720_8000.mp4存在,删除xxx_yyy_720_3800.mp4
  • 如果只有一个文件xxx_yyy_720_8000.mp4不是一个文件xxx_yyy_720_3800.mp4,不执行任何操作。

任何帮助将不胜感激。

答案1

使用findgawk

  1. 安装gawk

    sudo apt-get install gawk
    
  2. 进入您的文件夹或将命令.后的替换find为您的文件夹名称,例如:find ~/my_video_duplicates f -iname …

  3. 测试命令

    以下命令仅显示删除候选

    find . -type f -iname "*_8000.mp4" -print0 | \
        while read -d $'\0' file; do \
            gawk -F_ '{ \
                a=gensub(/\_8000\./, "_3800.", "g" , $0); \
                system("if [ -f \""a"\" ]; then echo \""a"\" will be deleted; fi")}' <<< "$file";\
        done
    
  4. 再次检查您是否在正确的文件夹中,或将命令.后的替换find为您的文件夹名称,例如:find ~/my_video_duplicates f -iname …

  5. 如果确定,请运行以下命令

    find . -type f -iname "*_8000.mp4" -print0 | \
        while read -d $'\0' file; do \
            gawk -F_ '{ \
                a=gensub(/\_8000\./, "_3800.", "g" , $0); \
                system("if [ -f \""a"\" ]; then rm \""a"\"; fi")}' <<< "$file";\
        done
    

例子

  • 起始情况

    % ls -og
    total 3
    -rw-rw-r-- 1 0 Jul 14 19:37 xxxx_yyy_720_3800.mp4
    -rw-rw-r-- 1 0 Jul 14 19:20 xxxx_yyy_720_8000.mp4
    -rw-rw-r-- 1 0 Jul 14 19:21 aaaa_yyy_720_8000.mp4
    
  • 试运行

    % find . -type f -iname "*_8000.mp4" -print0 | \
        while read -d $'\0' file; do \
            gawk -F_ '{ \
                a=gensub(/\_8000\./, "_3800.", "g" , $0); \
                system("if [ -f \""a"\" ]; then echo \""a"\" will be deleted; fi")}' <<< "$file";\
        done
    ./xxxx_yyy_720_3800.mp4 will be deleted
    
  • 移除

    % find . -type f -iname "*_8000.mp4" -print0 | \
        while read -d $'\0' file; do \
            gawk -F_ '{ \
                a=gensub(/\_8000\./, "_3800.", "g" , $0); \
                system("if [ -f \""a"\" ]; then rm \""a"\"; fi")}' <<< "$file";\
        done
    
  • 最后的情况

    % ls -og
    total 2
    -rw-rw-r-- 1 0 Jul 14 19:20 xxxx_yyy_720_8000.mp4
    -rw-rw-r-- 1 0 Jul 14 19:21 aaaa_yyy_720_8000.mp4
    

答案2

使用BashShell

[ -f "file" ]检查文件名是否存在,并且是否是普通文件(例如不是目录或符号链接)

"${name/%x/y}"用替换x的后缀。$namey

xxx_yyy_720_3800.mp4因此,仅当xxx_yyy_720_8000.mp4存在xxxyyy在每种情况下和都相同时,才删除for所有*_*_720_3800.mp4 in当前目录:

for name in *_*_720_3800.mp4
do if [ -f "${name/%3800.mp4/8000.mp4}" ]
   then echo "$name"
   fi
done

如果您确定这样可以的话,请将echo其更改为。rm

相关内容