Commande Unix pour vérifier si deux lignes d'un fichier sont identiques?

24

Existe-t-il une commande Unix qui peut vérifier si deux lignes d'un fichier sont identiques?

Par exemple, considérez un fichier sentences.txt

This is sentence X
This is sentence Y
This is sentence Z
This is sentence X
This is sentence A
This is sentence B

On voit que la phrase

This is sentence X

est répété.

Y a-t-il une commande qui peut rapidement détecter cela, afin que je puisse peut-être l'exécuter comme ça -

$ cat sentences.txt | thecommand
Line 1:This is sentence X
Line 4:This is sentence X
Code bleu
la source

Réponses:

40

Voici une façon d'obtenir la sortie exacte que vous recherchez:

$ grep -nFx "$(sort sentences.txt | uniq -d)" sentences.txt 
1:This is sentence X
4:This is sentence X

Explication:

L'intérieur $(sort sentences.txt | uniq -d)répertorie chaque ligne qui se produit plus d'une fois. L'extérieur grep -nFxrecherche à nouveau sentences.txtles -xcorrespondances exactes avec l'une de ces lignes -Fet ajoute leur numéro de ligne-n

grebneke
la source
Votre modification m'a à peine battu de poster la même réponse exacte. +1
casey
Donc la syntaxe $ (commande) fonctionne comme une sorte de remplacement?
CodeBlue
2
@CodeBlue - oui. C'est ce qu'on appelle la substitution de commande
grebneke
8
sort sentences.txt | uniq -d | grep -nFxf - sentences.txtserait un peu plus efficace et éviterait des arg list too longproblèmes potentiels .
Stéphane Chazelas
10

Pas exactement ce que vous voulez, mais vous pouvez essayer de combiner sortet uniq -c -d:

aularon@aularon-laptop:~$ cat input
This is sentence X
This is sentence Y
This is sentence Z
This is sentence X
This is sentence A
This is sentence B

aularon@aularon-laptop:~$ sort input | uniq -cd
      2 This is sentence X
aularon@aularon-laptop:~$ 

2voici le nombre de doublons trouvés pour la ligne, à partir de man uniq:

   -c, --count
          prefix lines by the number of occurrences

   -d, --repeated
          only print duplicate lines
aularon
la source
6

SI le contenu du fichier awktient en mémoire est bon pour cela. Le one-liner standard dans comp.lang.awk (je ne peux pas rechercher une instance de cette machine mais il y en a plusieurs chaque mois) pour simplement détecter qu'il y a duplication est celui awk 'n[$0]++'qui compte les occurrences de chaque valeur de ligne et imprime toute occurrence (s) autre que le premier, car l'action par défaut est print $0.

Pour afficher toutes les occurrences, y compris la première, dans votre format, mais éventuellement dans un ordre mixte lorsque plusieurs valeurs sont dupliquées, devient un peu plus difficile:

awk <sentences.txt ' !($0 in n) {n[$0]=NR;next} \
    n[$0] {n[$0]=0; print "Line "n[$0]":"$0} \
    {print "Line "NR":"$0} '

Montré sur plusieurs lignes pour plus de clarté, vous exécutez généralement ensemble en utilisation réelle. Si vous faites cela souvent, vous pouvez mettre le awkscript dans un fichier avec awk -f, ou bien sûr le tout dans un script shell. Comme la plupart des choses simples, awkcela peut être fait de manière très similaire avec perl -n[a].

dave_thompson_085
la source