入力ファイルには次のものがあります
#Start para
0 hello dq
1 world dq
2 welcomes dq
3 you dq
#Start para
0 how tq
1 are tq
2 you tq
#Start para
0 say dq
1 hello dq
2 to dq
3 the dq
4 world dq
以下のような他のファイルに移動したいと思います。
#Start para
3 you dq
2 welcomes dq
1 world dq
0 hello dq
#Start para
2 you tq
1 are tq
0 how tq
#Start para
4 world dq
3 the dq
2 to dq
1 hello dq
0 say dq
sed
またはを使用してこれをどのように実行できますかawk
?基本的に段落を反転したいと思います#Start para
。ただし、段落の順序は同じままでなければなりません。
答え1
唯一のものが#
ブロックの始まりであれば、試してみることができawk
ます
$ awk -F'\n' 'BEGIN{RS="#"}NR>1{print "#"$1;for(i=NF-1;i>1;i--)print $i}' file
結果:
#Start para
3 you dq
2 welcomes dq
1 world dq
0 hello dq
#Start para
2 you tq
1 are tq
0 how tq
#Start para
4 world dq
3 the dq
2 to dq
1 hello dq
0 say dq
答え2
そしてsed
:
sed '/#Start para/{x;G;s/^\n//;p;s/.*//;x;d};G;s/\n$//;h;$!d' input.file
次を含む行の場合は、#Start para
変更の最後にeを追加します。hold space
x
パターン空間<->スペアスペースその後、データを返します。捕まえるG
それを添付する模様。 (H
ホールドに取り付けてからパターンに戻って同じ操作を実行できますg
。)予約済みスペースが空の場合、パターンスペースは空白行で始まるため、削除され集められた行がs/^\n//
印刷p
されます。次のコマンド(まで}
)は、保持スペースとパターンスペースをクリーンアップして次の行に移動するためのものです。
他の行(含まれていない#Start para
)の場合、予約済みG
スペースをパターンに追加し、空の行を削除し(予約済みスペースが空の場合)、パターンスペースを予約済みスペースに入れ、新しいループを開始して行以外のd
場合を削除します。最後の行。最後の行の場合、デフォルトで形成されたパターン空間が印刷されます。
答え3
より保守的で難解なアプローチのために…
awk '
/^#/ { printf "%s",out ; print ; out = "" }
/^[0-9]/ { out = $0 RS out }
END { printf "%s",out }
'
答え4
以下は3つのアプローチです。
sed 's/^#/\n#/' file |
perl -00lne '@A=split(/\n/); print shift(@A); print join "\n", reverse @A' |
grep .
説明する
- この
sed
コマンドは、で始まる各行の前に改行文字を追加します#
。これにより、Perlの短絡モードを使用できます(下記参照)。 パールオプション:
-00
「ショートモード」を有効にすると、「行」は2文字で定義されます\n
。-l
:末尾の改行を削除し、\n
各呼び出しprint
にaを追加します。-n
:入力ファイルを1行ずつ(またはこの場合はセクションごとに)読み込みます。-e
:各行で実行するスクリプトです。
Perlスクリプト:
@A=split(/\n/);
:この行(段落)を配列に分割して、@A
個々の行(ここでは段落ではなく実際の行)を配列の要素にします。print shift(@A);
@A
:(ヘッダ行)の最初の要素を削除して印刷します。print join "\n", reverse @A'
:残りの要素を反転し、@A
文字を連結して\n
印刷します。
grep .
:追加された空白行を削除する汚れたハッキングですsed
。これにより、少なくとも1つの文字を含むすべての行が印刷されます。