Mit sed , wie würde man Text nach einem Zeichen einfügen, das vor (oder nach) einer Zeichenfolge durch N steht Vorkommnisse. Nehmen wir als Beispiel an, dass die zu bearbeitende Textzeile die folgende ist:
command -some -args -c 'a quoted section;some;lines;of code;keyword;more lines;etc();'
Nachdem Sie diese Zeile in einer Textdatei gefunden haben (vielleicht durch die eindeutige Zeichenfolge command ), möchte ich Text nach dem zweiten (N=2) Semikolon vor keyword einfügen (d. h. das Semikolon, das lines trennt und of ). Ich möchte speziell sed verwenden für den Zweck.
Wenn Sie mit diesem Beispiel fortfahren, wäre die erwartete Ausgabe:
command -some -args -c 'a quoted section;some;lines;INSERTED_STRING;of code;keyword;more lines;etc();'
wobei INSERTED_STRING; (sed bereitgestellt, z. B. über eine Shell-Variable) wurde an der gewünschten Position eingefügt.
Akzeptierte Antwort:
Ich bevorzuge es einfach:
sed '/command/s/[^;]*;keyword/INSERTED_STRING;&/'
um zwei Felder vor dem Schlüsselwort einzufügen. Die allgemeine Lösung wäre
sed "/command/s/\([^;]*;\)\{$N\}keyword/INSERTED_STRING;&/"
Beachten Sie jedoch, dass das N hat im Vergleich zu Ihrer Frage ein Offnet von 1:Hier N=2 bedeutet zwei Felder zwischen der Einfügung und dem keyword zu haben .
Erklärung:/command/ wählt nur Zeilen mit command aus , sodass andere Zeilen unberührt bleiben. ([^;]*;\) stimmt mit einem Feld (einer Folge von Nicht-Semikolons) einschließlich des folgenden Semikolons überein. Indem Sie ihm \{$N\} folgen das Muster entspricht $N Felder. Das folgende keyword vervollständigt dies, um keyword abzugleichen und das $N Felder davor. Das Ersetzungsmuster besteht aus dem eingefügten String und & , die durch alles ersetzt wird, was abgeglichen wurde (also war es am Ende kein Ersatz, sondern eine Einfügung).
Gekürzt und besser lesbar mit erweiterten regulären Ausdrücken:
sed -E "/command/s/([^;]*;){$N}keyword/INSERTED_STRING;&/"