Suchen Sie in einer durch Leerzeichen getrennten Textdatei in der ersten Spalte nach einem Muster. Wenn Sie eines finden, behalten Sie das erste Vorkommen und löschen Sie die anderen Zeilen:
Eingabe (Muster = 1234):
1234 1111 2222
5678 3333 4444
1234 5678 9012
5678 1234 5678
1234 9786 5432
Erwartete Ausgabe:
1234 1111 2222
5678 3333 4444
5678 1234 5678
Antwort1
Sie möchten also alle Zeilen drucken, deren erstes Feld nicht der angegebene Wert ist, und die erste Zeile drucken, in der es übereinstimmt.
awk -vF="$1" '{ if ($1 != F) { print; } else {if (!seen) { print ; seen=1}}}'
Nutzt die Tatsache, dass AWK-Variablen ( seen
in diesem Fall) anfangs einen Wert von 0 haben.
Antwort2
Behalten Sie die erste übereinstimmende Zeile und entfernen Sie alle nachfolgenden übereinstimmenden Zeilen mit GNU sed:
sed -e '/^1234/{x;/./!{x;h;b;};d}' file
Erläuterung:
/^1234/
wenn Musterpuffer übereinstimmt ^1234
x
- Muster- und Haltepuffer vertauschen (Beim ersten Treffer ist der Haltepuffer leer, sodass der Musterpuffer nun – und das ist entscheidend – leer ist)
/./!
- Ist der Musterpuffer jetzt leer?
{x;h;b;}
- dann Muster austauschen (x) und Puffer halten (dadurch wird die aktuelle Zeile wieder in den Musterpuffer gelegt), Musterpuffer in den alten Puffer kopieren (h) und zum Ende der Ausführung für diese Zeile verzweigen (b) - d. h. die nächste Zeile laden und den Sed-Code erneut starten. Das abschließende (d) Löschen wird nicht ausgeführt.
d
- Nach der ersten Übereinstimmung enthält der Hold-Puffer eine Kopie der übereinstimmenden Zeile, sodass der obige Block {x;h;b;} nicht ausgeführt wird. Stattdessen wird die aktuelle Zeile gelöscht, das Programm beendet, die nächste Zeile wird in den Musterpuffer geladen und das Programm startet erneut.