web-dev-qa-db-ja.com

2つのパターン間の(およびそれを含む)行を印刷する

行末にCKがある行からgreppingを開始し、行の末尾にDがある場合はgreppingを停止します。私は試した grep "$CK" "$D" file..txt、しかしそれはうまくいきませんでした。

入力:

kkkkkkkkkkk   
jjjjjjjjjjjjjjjjjj  
gggggggggggg/CK  
JHGHHHHHHHH   
HJKHKKLKLLL   
JNBHBHJKJJLKKL  
JLKKKLLKJLKJ/D  
GGGGGGGGGGGGGG  
GGGGGGGGGGGGGG

望ましい出力:

gggggggggggg/CK  
JHGHHHHHHHH   
HJKHKKLKLLL   
JNBHBHJKJJLKKL  
JLKKKLLKJLKJ/D
17
Rana Khan

awk または sed を使用することをお勧めします

awk '/CK$/,/D$/' file.txt

OR

sed -n '/CK$/,/D$/p' file.txt

grep を主張する場合、GNU grep way

grep -oPz '(?s)(?<=\n)\N+CK\n.*?D(?=\n)' file.txt

ここに

-P Perl-regexpをアクティブにします

-z行区切りをNULに設定します。これにより、grepはファイル全体を1行として表示します。

-o一致するものだけを出力します

(?s) PCRE_DOTALLをアクティブにするので、.は、任意の文字または改行を検索します

\Nは改行以外のすべてに一致します

.*?が見つかります。非貪欲モードで

(?<=..)は後読みアサーションです

(?=..)は先読みアサーションです

22
iruvar

BSD grepを使用している場合(Perl regex param -Pはサポートされていません)、次の回避策があります。

grep -o "aaa.*cdn" <(paste -sd_ file) | tr '_' '\n'

これは、すべての行を連結し(新しい行を_文字で置き換える)、1行のパターンをチェックし、行を元の状態に拡張することによって機能します。

GNU grepを使用している場合、grepで複数行の一致を実現できますが、grepにはPerl-regexpを使用する必要があります(-P)別の answer で述べられているように、brew install grepを介してGNU grepをmacOSにインストールして使用できます。代わりにggrep


または、複数行のパターンをサポートする pcregrep を使用することもできます(-M)。


exコマンドを使用することもできます。例:

ex +"/aaa/;/cdn/p" -scq! file
0
kenorb