この質問を見つけて私の問題の99%を解決しましたが、終わりのパターンを^
。
sed - 行が条件に一致すると、パターン範囲に一致する行を印刷します。
これは私のデータであり、行の先頭で閉じる括弧を一致させる必要があります。
(
Device=B
Data=asdfasdf(qwfw)
Lorem=Ipsum
)
(
Device=A
Data=asdfasdf(aewf)
Lorem=Ipsum
)
(
Device=B
Data=asdfasdf(wef)
)
(
Device=A
Data=asdfasdf(jalks)
)
(
Device=B
Data=asdfasdf(asf)
)
(
Device=C
Data=asdfasdf(asfew)
Lorem=Ipsum
)
このコマンドを試していますが、何も一致しません。
sed -n '/(/{:a;N;/^)/!ba;/Device=A/p}' file
削除すると、^
以下が返されます。
-> % sed -n '/(/{:a;N;/)/!ba;/Device=A/p}' test
(
Device=A
Data=asdfasdf(aewf)
(
Device=A
Data=asdfasdf(jalks)
私がここで何を見逃しているのか知っている人はいますか?
sed バージョン
sed (GNU sed) 4.5
Copyright (C) 2018 Free Software Foundation, Inc.
答え1
^
パターンスペースに行を累積すると、次の行の先頭に一致するために使用できなくなりますが、代わりに\n
(挿入された改行文字)を使用する必要があります。
sed -n '/(/{:a;N;/\n)/!ba; /Device=A/p}' infile
とても好きですが、コスタスのソリューションそこに(通常、保持バッファを使用する方が簡単で/より良い):
sed 'H;/^(/h;/^)/!d;x;/Device=A/!d' infile
この場合、^
両方のモードにアンカーポイントが必要です。
答え2
sedでこれを実行しようとすると、awkが半世紀前に発明されたときに役に立たなかった神秘的な構造を使用します。 GNU awkを使用してマルチキャラRSとRTを実装します。
$ awk -v RS='\n)\n' '/Device=A/{ORS=RT; print}' file
(
Device=A
Data=asdfasdf(aewf)
Lorem=Ipsum
)
(
Device=A
Data=asdfasdf(jalks)
)
または awk を使用してください。
$ awk '{r=r $0 ORS} /^)/{if (r ~ /Device=A/) printf "%s", r; r=""}' file
(
Device=A
Data=asdfasdf(aewf)
Lorem=Ipsum
)
(
Device=A
Data=asdfasdf(jalks)
)
答え3
使用幸せ(以前はPerl_6として知られています)
~$ raku -e '.put for slurp.comb( /^^ \( \n "Device=A" \n [\N+ \n]+? \) $$ / );' file
#OR
~$ raku -e '.put for slurp.comb: /^^ \( \n "Device=A" \n [\N+ \n]+? \) $$ / ;' file
comb
簡単に言えば、楽は正反対ですsplit
。comb
一致する要素を抽出する正規表現一致子を提供できます。
上記のコードは、slurp
各行を自動的に切り捨てずにファイルを挿入します(すべての行を一度に読み取ります)。要素を抽出するには、Device=A
必要な一致行(\n
まだ存在する改行を含む)をリストします。
注:グループ化は、[\N+ \n]+?
改行文字ではなく、1つ以上の文字と改行文字からなる貪欲ではないシーケンスです。ここでこの... グループ化パターンは、貪欲にならないように1回以上発生します。\N
\n
[
]
+
?
出力例:
(
Device=A
Data=asdfasdf(aewf)
Lorem=Ipsum
)
(
Device=A
Data=asdfasdf(jalks)
)
答え4
sed ソリューションは次のとおりです。
$ sed -n '/=A/,/^)/p' infile | sed '/=A/i ('
(
Device=A
Data=asdfasdf(aewf)
Lorem=Ipsum
)
(
Device=A
Data=asdfasdf(jalks)
)