根据校验和重命名文件

根据校验和重命名文件

我有一个 md5sum 列表和很多文件,我想对它们进行校验和,然后根据 md5sum 列表重命名它们。

列表示例:

d4cd401ade018617629b39efed7b7be4  foo.bar
8fdb07ca55c164e0d5a69eff49fe800e  bar.foo
8b167d01009f066aaf2d6c1ba336d842  foobar

现在我想对当前目录中的每个文件进行校验,如果校验和与上面的列表匹配,则将其重命名为正确的列。

我怎样才能做到这一点?

答案1

首先,我不会声称这是最深刻的解决方案,但是,这是一种方法。

假设您有一个带有校验和和文件名的文件,filelist.txt那么您可以使用如下内容:

while read -r checksum fname; do for f in file*; do if [[ $checksum == $(md5sum "$f" | cut -d' ' -f1) ]]; then mv "$f" "$fname"; fi ; done ; done < filelist.txt

答案2

我还没有完全测试过,它只是理论上有效。需要时替换:

#! /bin/bash
for II in *
do
    if [ -f "$II" ]; then
        TMPV=$(md5sum "$II")
        MD="${TMPV%\ \ *}"
        TMPV=$(grep "$MD" hashes.txt)
        if [ ! -z "$TMPV" ]; then
            FN="${TMPV#*\ \ }"
            echo "Found: $II"
            echo "MD5 is: $MD"
            echo "Which matches $FN in hashes database"
            echo "Will Rename $II TO $FN"
            echo ""
            # CAREFUL, RENAME CMD: mv "$II" "$FN"
        fi;
    fi;
done;

正如我所说,还没有测试过,但它似乎适用于我的盒子。

答案3

我的想法:

  1. 首先,您需要对已知的校验和进行排序:sort checksums.txt > sorted_checksums.txt
  2. 为所有现有文件生成文件并对它们进行排序:md5sum * | sort > real_checksums.txt
  3. 连接这两个文件并排除具有相同新旧名称的记录:join -o "2.2 1.2" sorted_checksums.txt real_checksums.txt | awk '$1 != $2' > rename_pairs.txt
  4. 重命名所有文件:(从中cat rename_pairs.txt | xargs -L 1 echo mv删除以实际重命名文件)echoxargs

警告:仅当文件名中没有空格时这才有效。您可以用来awk 'NF != 2' sorted_checksums.txt real_checksums.txt检查这一点,如果有任何行被打印,那么您需要使用其他东西(可能是简单的perlpython程序的)来执行步骤 3 和 4。

答案4

将校验和读入关联数组,然后遍历文件并根据需要重命名它们。将重命名的文件放在单独的目录树中,以防新名称和旧名称重叠。

#!/bin/bash
mkdir renamed
typeset -A names
while read -r sum name; do
  names[$sum]=$name
done <list.md5sum
for file in *; do
  if [[ -f $file ]]; then
    sum=$(md5sum <"$file"); sum=${sum%% *}
    if [[ -n ${names[$sum]} ]]; then
      mv -- "$file" "renamed/${names[$sum]}"
    fi
  fi
done

相关内容