it-swarm.com.de

Wie wird jede Zeile verarbeitet, die als Ergebnis des Befehls grep empfangen wurde?

Nachdem ich den Befehl grep ausgeführt habe, habe ich einige Zeilen aus einer Datei abgerufen:

var=`grep xyz abc.txt`

Nehmen wir an, ich habe 10 Zeilen, die aus xyz bestehen.

Jetzt muss ich jede Zeile bearbeiten, die ich als Ergebnis des Befehls grep erhalten habe. Wie gehe ich dafür vor?

119
P_Jain

Eine der einfachsten Möglichkeiten besteht darin, die Ausgabe nicht in einer Variablen zu speichern, sondern sie direkt mit einer while/read-Schleife zu durchlaufen.

So etwas wie:

grep xyz abc.txt | while read -r line ; do
    echo "Processing $line"
    # your code goes here
done

Es gibt Variationen dieses Schemas, je nachdem, was genau Sie suchen.

Wenn Sie Variablen innerhalb der Schleife ändern müssen (und diese Änderung außerhalb der Schleife sichtbar sein soll), können Sie die Prozessersetzung wie in fedorquis Antwort :

while read -r line ; do
    echo "Processing $line"
    # your code goes here
done < <(grep xyz abc.txt)
218
Mat

Sie können die folgende while read-Schleife ausführen, die vom Ergebnis des grep-Befehls mit der sogenannten Prozessersetzung gespeist wird:

while IFS= read -r result
do
    #whatever with value $result
done < <(grep "xyz" abc.txt)

Auf diese Weise müssen Sie das Ergebnis nicht in einer Variablen speichern, sondern dessen Ausgabe direkt in die Schleife "injizieren".


Beachten Sie die Verwendung von IFS= und read -r gemäß den Empfehlungen in BashFAQ/001: Wie kann ich eine Datei (Datenstrom, Variable) Zeile für Zeile (und/oder Feld für Feld) lesen? :

Die Option -r zum Lesen verhindert die Interpretation des Backslash (normalerweise Als Backslash-Zeilenvorschubpaar verwendet, um über mehrere Zeilen fortzufahren oder um die Begrenzungszeichen zu umgehen .__). Ohne diese Option werden alle nicht umkehrbaren umgekehrten Schrägstriche in der Eingabe wird verworfen. Sie sollten fast immer die -r .__ verwenden. Option mit Lesen.

Im obigen Szenario verhindert IFS = das Beschneiden von führenden und nachlaufenden Leerraum. Entfernen Sie es, wenn Sie diesen Effekt wünschen.

In Bezug auf die Prozessersetzung wird dies auf der Seite bash-Hacker erläutert :

Prozessersetzung ist eine Form der Umleitung, bei der die Eingabe oder Die Ausgabe eines Prozesses (einige Befehlssequenzen) erscheint als temporäre Datei.

17
fedorqui

Ich würde empfehlen, awk anstelle von grep + etwas anderes zu verwenden.

awk '$0~/xyz/{ //your code goes here}' abc.txt

8
Julien Grenier

Oft spielt die Reihenfolge der Bearbeitung keine Rolle. GNU Parallel wird für diese Situation gemacht:

grep xyz abc.txt | parallel echo do stuff to {}

Wenn Sie die Verarbeitung eher wie folgt:

grep xyz abc.txt | myprogram_reading_from_stdin

und myprogram ist langsam, dann können Sie Folgendes ausführen:

grep xyz abc.txt | parallel --pipe myprogram_reading_from_stdin
0
Ole Tange