it-swarm-tr.com

çizgi içinde fark

Aradaki farklara baktığım bazı sql dökümlerim var. diff açıkçası bana iki satır arasındaki farkı gösterebilir, ancak virgülle ayrılmış değerler uzun listesindeki hangi değerlerin aslında satırların farklı olmasına neden olanları bulmaya çalışarak çıldırıyorum.

Belirli dosyalarda iki satır arasındaki karakter farklılıklarını göstermek için hangi aracı kullanabilirim?

120
user394

wdiff , bunun için Word-diff var.

Masaüstünde meld sizin için bir satırdaki farklılıkları vurgulayabilir.

96
alex

Git-diff kullanan başka bir yöntem:

git diff -U0 --Word-diff --no-index -- foo bar | grep -v ^@@

grep -v farkların pozisyonlarıyla ilgilenmiyorsa.

31
Deepak

Bunun için vimdiff kullandım.

İşte bir ekran görüntüsü (benim değil), oldukça iyi görünen küçük bir veya iki karakter farkı gösteriyor. A hızlı öğretici de .

24
Mark McKinstry

İşte size bir "..kendi ısırma köpek" yöntemi ...
diff sizi bu noktaya getirdi; sizi daha ileriye taşımak için kullanın ...

Örnek çizgi çiftlerini kullanarak çıktı ... bir SEKME belirtir

Paris in the     spring 
Paris in the the spring 
             vvvv      ^

A ca t on a hot tin roof.
a cant on a hot  in roof 
║   v           ^       ^

the quikc brown box jupps ober the laze dogs 
The☻qui ckbrown fox jumps over the lazy dogs 
║  ║   ^ ║      ║     ║    ║          ║     ^

İşte senaryo .. Sadece bir şekilde çizgi çiftlerini ortaya çıkarmanız gerekiyor .. (Bugünden önce sadece bir kez (iki kez?) senaryo benim için yeterliydi, bir gün için :) .. Bence bu kadar basit olmalı, ama kahve molası vereceğim ....

#
# Name: hair-of-the-diff
# Note: This script hasn't been extensively tested, so beware the alpha bug :) 
#   
# Brief: Uses 'diff' to identify the differences between two lines of text
#        $1 is a filename of a file which contains line pairs to be processed
#
#        If $1 is null "", then the sample pairs are processed (see below: Paris in the spring 
#          
# ║ = changed character
# ^ = exists if first line, but not in second 
# v = exists if second line, but not in first

bname="$(basename "$0")"
workd="/tmp/$USER/$bname"; [[ ! -d "$workd" ]] && mkdir -p "$workd"

# Use $1 as the input file-name, else use this Test-data
# Note: this test loop expands \t \n etc ...(my editor auto converts \t to spaces) 
if [[ "$1" == '' ]] ;then
  ifile="$workd/ifile"
{ while IFS= read -r line ;do echo -e "$line" ;done <<EOF
Paris in the spring 
Paris in the the spring
A cat on a hot tin roof.
a cant on a hot in roof
the quikc brown box jupps ober the laze dogs 
The\tquickbrown fox jumps over the lazy dogs
EOF
} >"$ifile"
else
  ifile="$1"
fi
#
[[ -f "$ifile" ]] || { echo "ERROR: Input file NOT found:" ;echo "$ifile" ;exit 1 ; }
#  
# Check for balanced pairs of lines
ilct=$(<"$ifile" wc -l)
((ilct%2==0)) || { echo "ERROR: Uneven number of lines ($ilct) in the input." ;exit 2 ; }
#
ifs="$IFS" ;IFS=$'\n' ;set -f
ix=0 ;left=0 ;right=1
while IFS= read -r line ;do
  pair[ix]="$line" ;((ix++))
  if ((ix%2==0)) ;then
    # Change \x20 to \x02 to simplify parsing diff's output,
    #+   then change \x02 back to \x20 for the final output. 
    # Change \x09 to \x01 to simplify parsing diff's output, 
    #+   then change \x01 into ☻ U+263B (BLACK SMILING FACE) 
    #+   to the keep the final display columns in line. 
    #+   '☻' is hopefully unique and obvious enough (otherwise change it) 
    diff --text -yt -W 19  \
         <(echo "${pair[0]}" |sed -e "s/\x09/\x01/g" -e "s/\x20/\x02/g" -e "s/\(.\)/\1\n/g") \
         <(echo "${pair[1]}" |sed -e "s/\x09/\x01/g" -e "s/\x20/\x02/g" -e "s/\(.\)/\1\n/g") \
     |sed -e "s/\x01/☻/g" -e "s/\x02/ /g" \
     |sed -e "s/^\(.\) *\x3C$/\1 \x3C  /g" \
     |sed -n "s/\(.\) *\(.\) \(.\)$/\1\2\3/p" \
     >"$workd/out"
     # (gedit "$workd/out" &)
     <"$workd/out" sed -e "s/^\(.\)..$/\1/" |tr -d '\n' ;echo
     <"$workd/out" sed -e "s/^..\(.\)$/\1/" |tr -d '\n' ;echo
     <"$workd/out" sed -e "s/^.\(.\).$/\1/" -e "s/|/║/" -e "s/</^/" -e "s/>/v/" |tr -d '\n' ;echo
    echo
    ((ix=0))
  fi
done <"$ifile"
IFS="$ifs" ;set +f
exit
#
6
Peter.O

wdiff aslında Word-by-Word dosyalarını karşılaştırmak için çok eski bir yöntemdir. Dosyaları yeniden biçimlendirerek, ardından farkları bulmak ve tekrar geri vermek için diff kullanarak çalıştı. Ben kendim bağlam eklemeyi önerdim, böylece Word-Word-Word karşılaştırmak yerine, diğer 'bağlam' kelimeleri ile çevrili her Word ile bunu yapar. Bu, diff'in dosyalardaki yaygın pasajlarda, özellikle dosyalar çoğunlukla birkaç ortak kelime bloğuyla farklı olduğunda kendini daha iyi senkronize etmesini sağlar. Örneğin intihal için metni karşılaştırırken veya yeniden kullanırken.

dwdiff daha sonra wdiff öğesinden oluşturuldu. Ancak dwdiff bu metin yeniden biçimlendirme işlevini dwfilter öğesinde iyi etki için kullanır. Bu harika bir gelişmedir - bir metni diğeriyle eşleşecek şekilde yeniden biçimlendirebileceğiniz ve daha sonra herhangi bir satır satır grafik fark görüntüleyici kullanarak karşılaştırabileceğiniz anlamına gelir. Örneğin, "diffüz" grafik fark ile kullanma ....

dwfilter file1 file2 diffuse -w

Bu yeniden biçimlendiriyor file1 biçimini file2 ve görsel bir karşılaştırma için diffuse 'e verir. file2 değiştirilmez, böylece Word farklılıklarını doğrudan diffuse içinde düzenleyebilir ve birleştirebilirsiniz. Düzenlemek isterseniz file1, ekleyebilirsin -r hangi dosyanın yeniden biçimlendirileceğini tersine çevirmek için. Deneyin ve son derece güçlü olduğunu göreceksiniz!

Grafiksel fark (yukarıda gösterilen) tercihim diffuse , çok daha temiz ve daha kullanışlı hissettirdiği için. Ayrıca bağımsız bir python programıdır, bu da diğer UNIX sistemlerine kurulum ve dağıtımın kolay olduğu anlamına gelir.

Diğer grafik farkların çok fazla bağımlılığı var gibi görünüyor, ancak kullanılabilir (seçim). Bunlar arasında kdiff3 veya xxdiff .

5
anthony

@ Peter.O's solution öğesini temel alarak bir dizi değişiklik yapmak için yeniden yazdım.

enter image description here

  • Farklılıkları göstermek için renk kullanarak her satırı yalnızca bir kez yazdırır.
  • Herhangi bir geçici dosya yazmaz, bunun yerine her şeyi pipetler.
  • İki dosya adı girdiğinizde her dosyadaki karşılık gelen satırları karşılaştırabilirsiniz. ./hairOfTheDiff.sh file1.txt file2.txt
  • Aksi takdirde, orijinal biçimi (önceki satırla karşılaştırılması gereken her ikinci satırın bulunduğu tek bir dosya) kullanırsanız, artık basitçe ekleyebilirsiniz; hiçbir dosyanın okunması gerekmez. Kaynaktaki demo 'a bir bakın; bu, paste ve çoklu dosya tanımlayıcıları kullanarak iki ayrı giriş için de dosyalara ihtiyaç duymamak için süslü borulara kapı açabilir.

Vurgulama olmaması, karakterin her iki satırda olduğu, vurgulama ise birincide olduğu ve kırmızı, ikincisinde olduğu anlamına gelir.

Renkler, komut dosyasının üstündeki değişkenler aracılığıyla değiştirilebilir ve hatta farklılıkları ifade etmek için normal karakterleri kullanarak renklerden tamamen vazgeçebilirsiniz.

#!/bin/bash

same='-' #unchanged
up='△' #exists in first line, but not in second 
down='▽' #exists in second line, but not in first
reset=''

reset=$'\e[0m'
same=$reset
up=$reset$'\e[1m\e[7m'
down=$reset$'\e[1m\e[7m\e[31m'

timeout=1


if [[ "$1" != '' ]]
then
    paste -d'\n' "$1" "$2" | "$0"
    exit
fi

function demo {
    "$0" <<EOF
Paris in the spring 
Paris in the the spring
A cat on a hot tin roof.
a cant on a hot in roof
the quikc brown box jupps ober the laze dogs 
The quickbrown fox jumps over the lazy dogs
EOF
}

# Change \x20 to \x02 to simplify parsing diff's output,
#+   then change \x02 back to \x20 for the final output. 
# Change \x09 to \x01 to simplify parsing diff's output, 
#+   then change \x01 into → U+1F143 (Squared Latin Capital Letter T)
function input {
    sed \
        -e "s/\x09/\x01/g" \
        -e "s/\x20/\x02/g" \
        -e "s/\(.\)/\1\n/g"
}
function output {
    sed -n \
        -e "s/\x01/→/g" \
        -e "s/\x02/ /g" \
        -e "s/^\(.\) *\x3C$/\1 \x3C  /g" \
        -e "s/\(.\) *\(.\) \(.\)$/\1\2\3/p"
}

ifs="$IFS"
IFS=$'\n'
demo=true

while IFS= read -t "$timeout" -r a
do
    demo=false
    IFS= read -t "$timeout" -r b
    if [[ $? -ne 0 ]]
    then
        echo 'No corresponding line to compare with' > /dev/stderr
        exit 1
    fi

    diff --text -yt -W 19  \
        <(echo "$a" | input) \
        <(echo "$b" | input) \
    | \
    output | \
    {
        type=''
        buf=''
        while read -r line
        do
            if [[ "${line:1:1}" != "$type" ]]
            then
                if [[ "$type" = '|' ]]
                then
                    type='>'
                    echo -n "$down$buf"
                    buf=''
                fi

                if [[ "${line:1:1}" != "$type" ]]
                then
                    type="${line:1:1}"

                    echo -n "$type" \
                        | sed \
                            -e "s/[<|]/$up/" \
                            -e "s/>/$down/" \
                            -e "s/ /$same/"
                fi
            fi

            case "$type" in
            '|')
                buf="$buf${line:2:1}"
                echo -n "${line:0:1}"
                ;;
            '>')
                echo -n "${line:2:1}"
                ;;
            *)
                echo -n "${line:0:1}"
                ;;
            esac
        done

        if [[ "$type" = '|' ]]
        then
            echo -n "$down$buf"
        fi
    }

    echo -e "$reset"
done

IFS="$ifs"

if $demo
then
    demo
fi
4
Hashbrown

İşte basit bir astar:

diff -y <(cat a.txt | sed -e 's/,/\n/g') <(cat b.txt | sed -e 's/,/\n/g')

Buradaki fikir, sed kullanarak virgüllerin (veya hangi sınırlayıcıyı kullanmak istediğiniz) yeni satırlarla değiştirmektir. diff sonra gerisini halleder.

3
user82160
  • xxdiff: Başka bir araç, önce kurulması gereken xxdiff (GUI) aracıdır.
  • e-tablo: Veritabanı verileri için .csv kolayca oluşturulur ve (A7==K7) ? "" : "diff" veya benzeri eklenmiş ve kopyalanmış.
2
user unknown

Sorunuzu doğru okuyorsam, diff -y bu tür şeyler için.

Hangi çizgilerin farklılıkları ortaya çıkardığını bulmak için yan yana karşılaştırmayı karşılaştırmak çok daha basittir.

1
rfelsburg

Komut satırında, dosyaları karşılaştırmadan önce yeni satırlar eklediğimden emin olurum. Sed, awk, Perl veya herhangi bir şeyi sistematik bir şekilde satır sonları eklemek için kullanabilirsiniz - çok fazla eklemediğinizden emin olun.

Ama en iyisi, vim'i Word farklılıklarını vurguladığı gibi kullanmak olduğunu görüyorum. vim çok fazla fark yoksa ve farklar basitse iyidir.

1
asoundmove

Aynı sorunu yaşadım ve PHP Fine Diff , ayrıntı düzeyini belirtmenize izin veren çevrimiçi bir araç ile çözdüm. Teknik olarak bir * nix aracı olmadığını biliyorum, ama sadece bir kerelik, bir karakter seviyesi farkı yapmak için bir program indirmek istemedim.

1
pillravi

kdiff Linux'ta standart GUI fark görüntüleyicisi haline geliyor. xxdiff ile benzerdir, ancak bence kdiff3 daha iyidir. "Belirli dosyalarda iki satır arasındaki kesin karakter farklarını" gösterme isteğiniz de dahil olmak üzere birçok şeyi iyi yapar.

1
Faheem Mitha