Ich habe eine Datei mit mehreren Zeilen. Ich möchte für jedes Wort, das in der Gesamtdatei erscheint, wissen, wie viele Zeilen dieses Wort enthalten, zum Beispiel:
0 hello world the man is world
1 this is the world
2 a different man is the possible one
Das erwartete Ergebnis ist:
0:1
1:1
2:1
a:1
different:1
hello:1
is:3
man:2
one:1
possible:1
the:3
this:1
world:2
Beachten Sie, dass die Anzahl für "Welt" 2 und nicht 3 beträgt, da das Wort in 2 Zeilen erscheint. Aus diesem Grund wäre die Übersetzung von Leerzeichen in Zeilenumbrüche nicht die exakte Lösung.
text-processing
Netzsooc
quelle
quelle
Antworten:
Eine weitere Perl-Variante mit List :: Util
quelle
Straightfoward-ish in Bash:
Betrachten Sie die Daten:
und Formatierung nach Ihren Wünschen:
quelle
Es ist ein ziemlich einfaches Perl-Skript:
Die Grundidee besteht darin, die Eingabe zu durchlaufen. Teilen Sie sie für jede Zeile in Wörter auf und speichern Sie diese Wörter in einem Hash (assoziatives Array), um alle Duplikate zu entfernen. Führen Sie dann eine Schleife über dieses Array von Wörtern und fügen Sie eines zu einem Gesamtzähler für dieses Wort hinzu. Berichten Sie am Ende über die Wörter und ihre Anzahl.
quelle
Eine Lösung, die mehrere Programme von einer Shell aus aufruft:
fmt -1 words.txt | sort -u | xargs -Ipattern sh -c 'echo "pattern:$(grep -cw pattern words.txt)"'
Eine kleine Erklärung:
Das
fmt -1 words.txt
druckt alle Wörter aus, 1 pro Zeile, und| sort -u
sortiert diese Ausgabe und extrahiert nur die eindeutigen Wörter daraus.Um das Vorkommen eines Wortes in einer Datei zu zählen, kann man
grep
(ein Werkzeug zum Durchsuchen von Dateien nach Mustern) verwenden. Durch Übergeben der-cw
Option gibt grep die Anzahl der gefundenen Wortübereinstimmungen an. So können Sie die Gesamtzahl derpattern
Verwendungsvorfälle ermittelngrep -cw pattern words.txt
.Das Tool
xargs
ermöglicht es uns, dies für jedes einzelne Wort zu tun, das von ausgegeben wirdsort
. Dies-Ipattern
bedeutet, dass der folgende Befehl mehrmals ausgeführt wird, wobei jedes Vorkommen eines Musters durch ein Wort ersetzt wird, das von der Standardeingabe gelesen wirdsort
.Die Indirektion mit
sh
ist erforderlich, daxargs
nur ein einzelnes Programm unter seinem Namen ausgeführt werden kann und alles andere als Argumente übergeben wird.xargs
behandelt keine Dinge wie die Ersetzung von Befehlen. Der$(...)
Befehl is substitution im obigen Snippet ersetzt die Ausgabe vongrep
inecho
und ermöglicht die korrekte Formatierung. Da wir die Befehlsersetzung benötigen, müssen wir densh -c
Befehl verwenden, der alles, was er erhält, als Argument in seiner eigenen Shell ausführt.quelle
fmt -1 words.txt | sort | uniq -c | awk '{ print $2 ":" $1 }'
sort | uniq -c
effizienter alssort -u
?Eine andere einfache Alternative wäre die Verwendung von Python (> 3.6). Diese Lösung hat das gleiche Problem wie die von @Larry in seinem Kommentar erwähnte .
Eine explizitere Version der obigen Version:
Ausgabe:
Das obige setzt auch voraus, dass sich words.txt im selben Verzeichnis wie script.py befindet . Beachten Sie, dass sich dies nicht wesentlich von anderen hier angebotenen Lösungen unterscheidet, aber vielleicht wird es jemand nützlich finden.
quelle
Ich versuche es mit awk zu machen:
count.awk :
Führen Sie es aus:
quelle
Eine reine Bash-Antwort
Ich habe in jeder Zeile eindeutige Wörter wiederholt und an übergeben
uniq -c
edit: ich habe glenns antwort nicht gesehen. Ich fand es seltsam, keine Bash-Antwort zu sehen
quelle
Einfach, aber egal, ob die Datei oft gelesen wird:
BEARBEITEN: Trotz der Konvertierung von Leerzeichen in Zeilenumbrüche werden Zeilen gezählt, bei denen jedes Wort vorkommt und nicht die Vorkommen der Wörter selbst. Es gibt das Ergebnis:
Dies ist zeichenweise identisch mit dem Beispielergebnis von OP.
quelle
translating blanks to newline chars wouldn't be the exact solution
.sed 's/ /\n/g' | sort | uniq -c
nicht funktionieren würde, weil es die Antwort 3 für die Welt geben würde, aber das ist nicht das, was diese Antwort tut. Es zählt die Zeilen, in denen die Wörter vorkommen, und nicht die Vorkommen selbst korrekt, genau wie es OP wollte.read -r
hier.