特定のパターンの間にあるファイル内の行を特定の長さに切り捨てるにはどうすればよいでしょうか?

特定のパターンの間にあるファイル内の行を特定の長さに切り捨てるにはどうすればよいでしょうか?

パターン @TEST と enabled="true"> の間にある行のみを切り捨てる必要があるファイルが複数あります。一致がある場合、 と の間の文字列は@TEST50enabled="true">文字のみである必要があります。その他の行はすべてそのままにしておく必要があります。

例:

@TEST-TC_0010 @TEST RADIUS アカウンティング サーバーが RADIUS クライアントからアカウンティング要求パケットを受信したときにアカウンティング応答メッセージを送信しないことを確認します。" enabled="true">

上記の行を以下のように変更する必要があります。

@テストTC_0010@テストRADIUSアカウンティングサーバーが有効="true">

答え1

この場合、Perl の lookaround で grep を使用できます。

grep -oP '(?<=@TEST ).*(?=\" enabled=\"true\")' inputfile

式「(?<=)」は一致が始まるポイントを示し、式「(?=)」は一致が終了するポイントを示します。

「.*」は、開始点と終了点の間のすべてを返すように grep に指示します。

テスト入力を使用すると、上記の行は 157 文字を返します。

$ echo "Verify that the RADIUS accounting server should not send the Accounting-Response Message on Receiving the Accounting-Request Packet from the RADIUS Client" | wc -m
157

これをさらに最初の50文字だけに切り詰めたい場合は、cutを使用します。

$ grep -oP '(?<=@TEST ).*(?=\" enabled=\"true\")' inputfile | cut -c1-50
Verify that the RADIUS accounting server should no

結果をファイルに保存したい場合は、出力を別のファイルにパイプする必要があります。次のようなものを使用できます...

$ grep -oP '(?<=@TEST ).*(?=\" enabled=\"true\")' inputfile | cut -c1-50 >> outputfile

入力ファイルを上書きすることは、ある時点で元のデータを使用する必要がある可能性があるため、個人的にはお勧めしません。

したがって、ファイル内の他のすべてのエントリを保持し、enabled="true" の行のみを切り捨てる必要がある場合は、ツールを awk に変更する必要があります。

$ awk  -F'@TEST' '{if (/true/) print substr($3,2,50); else print $0}' inputfile >> outputfile

このワンライナーは、true に一致しないすべての行を変更せずに出力します。true に一致すると、行は 50 文字に切り捨てられます。ここでも、結果が出力ファイルにパイプされるため、元のデータを上書きすることはお勧めしません。

OP が質問に対して行った最新の編集に基づいて、私は awk ワンライナーを修正し、Beginner が提供した出力を再現しました。彼はコメントで awk が機能しないと述べています。OP が awk が機能しない理由について詳細を提供するまで、Ubuntu 16.04 で awk 4.1.3 を使用する場合、次の行は彼がこれまでに詳述した結果を返します。

awk  -F'@TEST' '{if (/true/) print "@TEST"$2,"@TEST",substr($3,2,50),"enabled=\"true\">"; else print $0}' inputfile >> outputfile

関連情報