テキストファイルの単一範囲の行を複製する方法を見つけようとしています。範囲はファイル内で一意の行で始まりますが、範囲はファイル内の複数の場所に存在する可能性のある行で終わります。
処理する必要のある入力例を次に示します。
I have no imagination so this sample text will Common be boring. But it does demonstrate the problem I am trying to solve. Common Hi mom! This is a unique line. And here is some more text that should be copied as well. Common Followed by text that should not be copied.
複製して変更する必要がある行は、ここで指摘するために太字で示されています。
必要な出力は次のとおりです。
I have no imagination so this sample text will Common be boring. But it does demonstrate the problem I am trying to solve. Common Hi mom! This is a changed line. And here is different more text that should be copied as well. Common This is a unique line. And here is some more text that should be copied as well. Common Followed by text that should not be copied.
追加の出力は、明確にするために太字で示されています。
次の行で始まる行の範囲を取得する必要があります:
This is a unique line
次の行で終わります:
Common
その行の範囲は、元の行の範囲の直前に挿入する必要があります。一致する行の範囲のコピーを少し変更する必要があります。
範囲を終了する「共通」行自体は、ファイル内の多くの場所で発生する可能性があります。
動作するawk
を思いついた スクリプトですが、必要以上に複雑に見えます。私のawk
スキルは存在しません。
/This is a unique line/{flag=1}
/Common/{
if (flag > 0) {
n=m;
sub("some","different",n);
sub("unique","changed",n);
print n "\n" $0 "\n" m;
m=""
};
flag=0
};
flag{
if (length(m) > 0) {
m=m "\n" $0
} else {
m=$0
}
}
!flag{ print }
これを実装するためのよりクリーンで冗長性の低い方法はありますか? awk
以外のオプションも利用できます 。 macOSで利用できる標準コマンドである必要があります。
承認された回答:
awk '/This is a unique line/,/Common/{
H = H RS $0
if ( $0 ~ /Common/ ) {
g = H
sub("\n","",g)
sub("some","different",g)
sub("unique","changed",g)
$0 = g H
} else { next }
}1' inputfile
これがsed
です コード(回答セクションで示した)をawk
に変換 。
あなたが持っているコードは、awk
のオン/オフを切り替える責任があることに注意してください。 行を追跡するための可変フラグ。しかし、一方、awk
range
を使用する場合とまったく同じことを、すでに内部で行っています。 演算子,