Kahden tiedoston vertailu bash-komentosarjassa?

Kuinka löytää kaksi tiedostoa, jotka vastaavat tietoja shell-komentosarjassa ja kopioida tietovarasto toisesta shell-tiedostosta?

#!/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 

Kirjoitin koodin, mutta se ei toiminut. Kuinka kirjoittaa se?

Kommentit

  • Oletko yrittänyt käyttää diff -komento?

Vastaa

Voit testata vain, onko kaksi tiedostot ovat samat, käytä 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 

-s flag to cmp tekee apuohjelmasta hiljaisen. cmp -kohdan poistumistila on nolla verrattaessa kahta identtistä tiedostoa. Tätä käytetään yllä olevassa koodissa tulostamaan viesti siitä, ovatko nämä kaksi tiedostoa identtisiä vai eivät.


Jos kaksi syötetiedostot sisältää tiedostopolkujen luettelon jota haluat verrata, käytä sitten kaksoissilmukkaa kuten näin:

  

Tässä tulos tuotetaan sekä päätelaitteessa että tiedostossa file-comparison.out.

Oletetaan, että mikään polunimi kahdessa syötetiedostossa ei sisällä upotettuja uusia rivejä.

Koodi lukee ensin kaikki tiedostojen polkut nimeksi taulukoksi, files1, käyttämällä mapfile. Teen tämän välttääkseni lukemasta kyseistä tiedostoa useammin kuin kerran, koska joudumme käymään läpi kaikki nämä polkut jokaisen polun nimen kohdalla toisessa tiedostossa. Huomaat, että sen sijaan, että luisin sisäisen silmukan $filelist1 -sivulta, minä vain toistan files1 -taulukon nimiä.

Kommentit

  • Tarvitsen kokonaisohjelman bash-kuoressa
  • @santhoshreddy Katso päivitetty vastaus.

vastaus

Helpoin tapa on käyttää komentoa diff.

esimerkki:

oletetaan, että ensimmäinen tiedosto on file1.txt ja hän sisältää:

I need to buy apples. I need to run the laundry. I need to wash the dog. I need to get the car detailed.` 

ja toisen tiedoston 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. 

sitten voimme käyttää diff-tiedostoa näyttämään meille automaattisesti, mitkä rivit eroavat kahden komennon sisältävän tiedoston välillä:

diff file1.txt file2.txt

ja tulosteen tulee olla:

 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. 

Katsotaanpa, mitä tämä lähtö tarkoittaa. Tärkeää on muistaa, että kun diff kuvaa näitä eroja sinulle, se tekee niin ohjeellisessa yhteydessä: se kertoo kuinka muuttaa ensimmäinen tiedosto niin, että se vastaa toista tiedostoa. Diff-lähdön ensimmäinen rivi sisältää:

  • ensimmäistä tiedostoa vastaavat rivinumerot,
  • kirjain (a lisäykselle, c muutokselle tai d poistolle )
  • toista tiedostoa vastaavat rivinumerot.

Yllä olevassa lähdössä ”2,4c2,4 ” tarkoittaa:” Rivit 2 4 ensimmäisessä tiedostossa on muutettava vastaamaan rivejä 2 4 toisessa tiedostossa. ” Sen jälkeen se kertoo meille, mitkä rivit ovat jokaisessa tiedostossa:

  • Rivit, joita edeltää <, ovat riviä ensimmäisestä tiedostosta;
  • rivit, joita edeltää> ovat riviä toisesta tiedostosta.
  • Kolme viivaa (”—”) vain erottavat tiedoston 1 ja tiedoston rivit.

Lähde

Vastaa

Tässä on puhdas bash-komentotiedosto tiedostojen vertaamiseksi:

#!/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 

tuottaa:

$ ./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. 

Kommentit tietyt komennot voidaan poistaa poistuaksesi ensimmäisestä nähdystä erosta ja jos haluat nähdä kaikki luetut rivit.

Katso sivu osoitteesta http://www.linuxjournal.com/content/reading-multiple-files-bash lisätietoja tiedostokuvaajista, kuten ”& 3”.

Ystävällisin terveisin … kippis, drl

kommentit

  • head on ulkoinen apuohjelma, mikä on $HOME/bin/context? Ja mitä kommentit tarkoittavat yläosassa?
  • Head näyttää syötteen. Se ei pelaa toisistaan erottelussa. Kuten joissakin muissa kohteissa, ” context ” on paikallinen osoittamaan ympäristökontekstia. Lisäämällä se meidän ei ’ ei tarvitse keskustella siitä, eroavatko käyttöjärjestelmien versiot ja hyödyllisyydet.
  • Vienti puuttui, kiitos huomanneet sen.
  • En vieläkään ymmärrä kommenttia ’.Mikä ’ s on ” ulkoinen käyttäjä ”, ja miksi haluat asettaa puhtaan komentosarjan polku bash?
  • Kirjoitamme koodia myymälällemme, joten polun asetukset voivat poiketa ulkoisilta käyttäjiltä. Lisätään, että jos näyttää tarpeelliselta jättää asetukset pois. Tämä on malli, joka on muokattu näyttämään tiedot ympäristöstä, jossa koodi suoritettiin. Jos se muutettaisiin tuotantokoodiksi, sanotaan asiakkaille, esittelykoodin sijaan ’ haluamme olla varmoja siitä, että mikään paikallisista poluistamme ei ole käytössä. kontekstille on suunniteltu siten, että jos tiedostoa ei löydy, mitään ei tapahdu, edes virhettä, mutta versioita ei ole luettelossa.

Vastaa

Sähköpostiosoitettasi ei julkaista. Pakolliset kentät on merkitty *