Diff mehrere Dateien, wahr, wenn alle nicht gleich sind

18

Ich habe eine Reihe von Dateien, ich möchte überprüfen, ob alle diese Dateien den gleichen Inhalt haben.

Mit welcher Befehlszeile könnte ich das überprüfen?

Die Verwendung könnte etwa sein:

$ diffseveral file1 file2 file3 file4

Ergebnis:

All files equals

ODER

Files are not all equals
Nicolas Raoul
quelle

Antworten:

27

Übergeben Sie mit GNU diff eine der Dateien als Argument --from-fileund beliebig viele andere als Operanden:

$ diff -q --from-file file1 file2 file3 file4; echo $?
0
$ echo >>file3
$ diff -q --from-file file1 file2 file3 file4; echo $?
Files file1 and file3 differ
1
Gilles 'SO - hör auf böse zu sein'
quelle
4

Wie wäre es mit:

md5sum * | awk 'BEGIN{rc=1}NR>1&&$1!=last{rc=0}{last=$1}END{exit rc}'

Berechnet den MD5-Wert für jede Datei und vergleicht dann jeden Eintrag mit dem nächsten. Dies wäre viel kürzer, wenn es falsch wäre, wenn es anders wäre:

md5sum * | awk 'NR>1&&$1!=last{exit 1}{last=$1}'

Es ist nicht nötig zu sortieren, da wir nur prüfen, ob sich welche unterscheiden.

Arcege
quelle
1
In der kürzeren Version sollte vermutlich $ 1 verwendet werden, da $ 0 einen eindeutigen Dateinamen enthält.
Xanpeng
2

Der folgende Code sollte ziemlich selbsterklärend sein. $#ist die Anzahl der Dateiargumente, die jeweils shifteinzeln verwendet werden. Verwendet cmp -sfür den stummen byteweisen Vergleich.

#!/bin/sh
# diffseveral

if [ $# -lt 2 ]; then
    printf '%s\n' "Usage: $0 file1 file2 [files ...]" >&2
    exit 2
fi

oldfile="$1"
shift

while [ $# -gt 0 ]; do
    newfile="$1"
    if ! cmp -s "$oldfile" "$newfile"; then
         echo 'Files differ.'
         exit 1;
    fi

    shift
done

echo 'All files identical.'
exit 0
jw013
quelle
0

Es können immer nur diffzwei gleichzeitig sein, aber es ist ziemlich einfach zu überprüfen, ob alle gleich sind:

if diff file1 file2 && diff file2 file3 && diff file3 file4; then
    echo All equal
else
    echo Not
fi

Wenn Sie genug haben, um eine Schleife zu rechtfertigen, verwenden Sie Folgendes:

alleq () {  
    for file; do 
        diff -q "$1" "$file" >/dev/null || return 1
    done
}

if alleq file1 file2 ...; then
    echo All equal
else 
    echo Not
fi
Kevin
quelle
Unbeholfen, wenn Sie fünfzig Dateien haben oder nicht wissen, wie viele
DarenW
1
@DarenW Klar, wenn du so viele hast, benutze einfach eine Schleife.
Kevin