Ich möchte die vorherige Zeile jedes Mal drucken, wenn eine Übereinstimmung gefunden wurde. Ich kenne grep -A
und -B
Optionen. Aber mein Solaris 5.10-Rechner unterstützt diese Optionen nicht.
Ich möchte eine Lösung, die nur sed
verwendet .
Foo.txt
:
Name is : sara
age is : 10
Name is : john
age is : 20
Name is : Ron
age is : 10
Name is : peggy
age is : 30
Out.txt
:
Name is : sara
Name is : Ron
Das Muster, das ich zuzuordnen versuche, war age is : 10
.
Meine Umgebung, Solaris 5.10.
Akzeptierte Antwort:
$ sed -n '/age is : 10/{x;p;d;}; x' Foo.txt
Name is : sara
Name is : Ron
Das obige wurde auf GNU sed getestet. Wenn sed von Solaris das Verketten von Befehlen mit Semikolons nicht unterstützt, versuchen Sie Folgendes:
$ sed -n -e '/age is : 10/{x;p;d;}' -e x Foo.txt
Name is : sara
Name is : Ron
Wie es funktioniert
sed hat einen Haltebereich und einen Musterbereich. Zeilenumbrüche werden in den Musterraum eingelesen. Die Idee dieses Skripts ist, dass die vorherige Zeile im Haltebereich gespeichert wird.
-
/age is : 10/{x;p;d;}
Wenn die aktuelle Zeile
age is : 10
enthält , dann tun:x
:Tauschen Sie das Muster aus und halten Sie die Leerstelle, sodass sich die vorherige Zeile im Musterbereich befindetp
:gibt die vorherige Zeile ausd
:Lösche den Musterbereich und beginne mit der Verarbeitung der nächsten Zeile -
x
Dies wird nur auf Zeilen ausgeführt, die
age is : 10
nicht enthalten . In diesem Fall speichert es die aktuelle Zeile im Haltebereich.
Das Gegenteil tun
Angenommen, wir möchten die Namen von Personen ausgeben, deren Alter nicht ist 10:
$ sed -n -e '/age is : 10/{x;d}' -e '/age is :/{x;p;d;}' -e x Foo.txt
Name is : john
Name is : peggy
Das obige fügt am Anfang einen Befehl hinzu, /age is : 10/{x;d}
, alle Alters-10 Leute zu ignorieren. Der folgende Befehl, /age is :/{x;p;d;}
, akzeptiert jetzt alle verbleibenden Alter.