Comment trouver deux fichiers correspondant aux données dans le script shell et dupliquer le magasin de données dans un autre fichier du shell?
#!/bin/bash file1="/home/vekomy/santhosh/bigfiles.txt" file2="/home/vekomy/santhosh/bigfile2.txt" while read -r $file1; do while read -r $file2 ;do if [$file1==$file2] ; then echo "two files are same" else echo "two files content different" fi done done
Jai écrit du code mais ça na pas fonctionné. Comment lécrire?
Commentaires
Réponse
Pour simplement tester si deux les fichiers sont identiques, utilisez cmp -s
:
#!/bin/bash file1="/home/vekomy/santhosh/bigfiles.txt" file2="/home/vekomy/santhosh/bigfile2.txt" if cmp -s "$file1" "$file2"; then printf "The file "%s" is the same as "%s"\n" "$file1" "$file2" else printf "The file "%s" is different from "%s"\n" "$file1" "$file2" fi
Le -s
Lindicateur sur cmp
rendra lutilitaire « silencieux ». Le statut de sortie de cmp
sera zéro lors de la comparaison de deux fichiers identiques. Ceci est utilisé dans le code ci-dessus pour imprimer un message indiquant si les deux fichiers sont identiques ou non.
Si vos deux fichiers dentrée contiennent une liste de chemins de fichiers que vous souhaitez comparer, puis utilisez une double boucle comme ceci:
Ici, le résultat est produit à la fois sur le terminal et dans le fichier file-comparison.out
.
On suppose quaucun chemin daccès dans les deux fichiers dentrée ne contient de sauts de ligne intégrés.
Le code lit dabord tous les chemins daccès dun des fichiers dans un tableau, files1
, en utilisant mapfile
. Je fais cela pour éviter davoir à lire ce fichier plus dune fois, car nous devrons parcourir tous ces chemins pour chaque chemin dans lautre fichier. Vous remarquerez quau lieu de lire à partir de $filelist1
dans la boucle interne, je viens de parcourir les noms dans le tableau files1
.
Commentaires
- Jai besoin dun programme complet dans le shell bash
- @santhoshreddy Voir la réponse mise à jour.
Réponse
Le moyen le plus simple est dutiliser la commande diff
.
exemple:
supposons que le premier fichier est file1.txt
et il contient:
I need to buy apples. I need to run the laundry. I need to wash the dog. I need to get the car detailed.`
et le deuxième fichier file2.txt
I need to buy apples. I need to do the laundry. I need to wash the car. I need to get the dog detailed.
alors nous pouvons utiliser diff pour nous afficher automatiquement les lignes qui diffèrent entre les deux fichiers avec cette commande:
diff file1.txt file2.txt
et le résultat sera:
2,4c2,4 < I need to run the laundry. < I need to wash the dog. < I need to get the car detailed. --- > I need to do the laundry > I need to wash the car. > I need to get the dog detailed.
Jetons un coup dœil à ce que signifie ce résultat. La chose importante à retenir est que lorsque diff vous décrit ces différences, il le fait dans un contexte normatif: il vous indique comment modifier le premier fichier pour quil corresponde au deuxième fichier. La première ligne de la sortie de diff contiendra:
- numéros de ligne correspondant au premier fichier,
- une lettre (a pour ajouter, c pour modifier ou d pour supprimer )
- numéros de ligne correspondant au deuxième fichier.
Dans notre sortie ci-dessus, « 2,4c2,4 « signifie: » Lignes 2 à 4 dans le premier fichier doit être modifié pour correspondre aux lignes 2 à 4 dans le deuxième fichier. » Il nous indique ensuite quelles sont ces lignes dans chaque fichier:
- Les lignes précédées dun < sont des lignes du premier fichier;
- les lignes précédées de> sont des lignes du deuxième fichier.
- Les trois tirets (« —« ) séparent simplement les lignes du fichier 1 et du fichier 2.
Réponse
Voici un pur script shell bash pour comparer des fichiers:
#!/usr/bin/env bash # @(#) s1 Demonstrate rudimentary diff using shell only. # Infrastructure details, environment, debug commands for forum posts. # Uncomment export command to run as external user: not context, pass-fail. # export PATH="/usr/local/bin:/usr/bin:/bin" set +o nounset LC_ALL=C ; LANG=C ; export LC_ALL LANG pe() { for _i;do printf "%s" "$_i";done; printf "\n"; } pl() { pe;pe "-----" ;pe "$*"; } db() { ( printf " db, ";for _i;do printf "%s" "$_i";done;printf "\n" ) >&2 ; } db() { : ; } C=$HOME/bin/context && [ -f "$C" ] && $C set -o nounset FILE1=${1-data1} shift FILE2=${1-data2} # Display samples of data files. pl " Data files:" head "$FILE1" "$FILE2" # Set file descriptors. exec 3<"$FILE1" exec 4<"$FILE2" # Code based on: # http://www.linuxjournal.com/content/reading-multiple-files-bash # Section 2, solution. pl " Results:" eof1=0 eof2=0 count1=0 count2=0 while [[ $eof1 -eq 0 || $eof2 -eq 0 ]] do if read a <&3; then let count1++ # printf "%s, line %d: %s\n" $FILE1 $count1 "$a" else eof1=1 fi if read b <&4; then let count2++ # printf "%s, line %d: %s\n" $FILE2 $count2 "$b" else eof2=1 fi if [ "$a" != "$b" ] then echo " File $FILE1 and $FILE2 differ at lines $count1, $count2:" pe "$a" pe "$b" # exit 1 fi done exit 0
produisant:
$ ./s1 Environment: LC_ALL = C, LANG = C (Versions displayed with local utility "version") OS, ker|rel, machine: Linux, 3.16.0-4-amd64, x86_64 Distribution : Debian 8.9 (jessie) bash GNU bash 4.3.30 ----- Data files: ==> data1 <== I need to buy apples. I need to run the laundry. I need to wash the dog. I need to get the car detailed. ==> data2 <== I need to buy apples. I need to do the laundry. I need to wash the car. I need to get the dog detailed. ----- Results: File data1 and data2 differ at lines 2, 2: I need to run the laundry. I need to do the laundry. File data1 and data2 differ at lines 3, 3: I need to wash the dog. I need to wash the car. File data1 and data2 differ at lines 4, 4: I need to get the car detailed. I need to get the dog detailed.
Les commentaires sur des commandes spécifiques peuvent être supprimées pour quitter à la première différence observée, et si vous souhaitez voir chaque ligne qui est lue.
Voir la page à http://www.linuxjournal.com/content/reading-multiple-files-bash pour plus de détails sur les descripteurs de fichiers tels que « & 3 ».
Meilleurs voeux … salutations, drl
Commentaires
-
head
est un utilitaire externe, et quest-ce que$HOME/bin/context
? Et que signifient les commentaires en haut? - Head affiche lentrée. Il ne joue pas séparément dans la différenciation. Comme pour certains autres éléments, » context » est local pour afficher le contexte de lenvironnement. En incluant cela, nous navons ‘ pas à discuter si les versions des systèmes dexploitation et des utilitaires diffèrent.
- Il y avait une exportation manquante, merci de lavoir remarqué.
- Je ne comprends toujours pas ‘ le commentaire.Quest-ce que ‘ est un » utilisateur externe « , et pourquoi voudriez-vous définir le chemin pour un script pur
bash
? - Nous écrivons du code pour notre boutique, les paramètres du chemin peuvent donc différer pour les utilisateurs externes. Nous ajoutons que sil semble nécessaire domettre nos paramètres. Il sagit dun modèle qui est modifié pour afficher les informations sur lenvironnement dans lequel le code a été exécuté. Sil devait être transformé en code de production, par exemple pour les clients, au lieu dun code de démonstration, nous ‘ voudrions être sûrs quaucun de nos chemins locaux nest utilisé. for context est conçu de sorte que si ce fichier nest pas trouvé, rien ne se produira, pas même une erreur, mais aucune version ne sera répertoriée.
diff
commande?