2012-10-30 15 views
5

awkを使用して複数行の式を解析しようとしています。それらのうちの1つは次のようになります。awkと複数行のマッチング(sub-regex)

_begin hello world ! 
_attrib0 123 
_attrib1 super duper 
_attrib1 yet another value 
_attrib2 foo 
_end 

_beginと_attrib1に関連付けられた値を抽出する必要があります。この例では、awkスクリプトは1行に1つ返さなければなりません。

hello world ! super duper yet another value 

使用する区切り文字はタブ(\ t)文字です。スペースは文字列内でのみ使用されます。

答えて

8

次awkスクリプトは、仕事をしていません:

#!/usr/bin/awk -f 
BEGIN { FS="\t"; } 
/^_begin/  { output=$2; } 
$1=="_attrib1" { output=output " " $2; } 
/^_end/  { print output; } 

あなたは、タブ(\tが)あなたの出力フィールドセパレータになりたいかを指定しませんでした。あなたがそうしたら、私に知らせて、私は答えを更新します。 (またはあなたがすることができます。それは些細なのです。)もちろん

、(私たちはハロウィーンに近づいているので)あなたが怖いの代替をしたい場合は、ここでの解決策はsedを使用して:

$ sed -ne '/^_begin./{s///;h;};/^_attrib1[^0-9]/{s///;H;x;s/\n/ /;x;};/^_end/{;g;p;}' input.txt 
hello world ! super duper yet another value 

はどのようにこの作品? Mwaahahaa、私はあなたに尋ねられてうれしいです。

  • /^_begin./{s///;h;}; - 私たちは_beginが表示されたら、それを剥ぎ取るとのsedの「バッファホールド」への行の残りの部分を格納します。
  • /^_attrib1[^0-9]/{s///;H;x;s/\n/ /;x;};と表示されている場合は、それを剥がしてホールドバッファに追加し、ホールドバッファとパターンスペースを交換し、改行をスペースで置き換えて、再びホールドバッファとパターンスペースを元に戻します。
  • /^_end/{;g;p;} - 終了したので、ホールドバッファをパターンスペースに引き出して印刷します。

これは、入力フィールドの区切り文字が1つのタブであることを前提としています。

とてもシンプルです。これまで誰がsedと言ったのは秘密だったのですか?

+0

_attrib11は、このスクリプトは、指定されたサンプルデータには、 '_attrib11'はありませんでした(_attrib1が一致する) – malat

+0

失敗しつつあります。もしあなたが好きなら、 '/^_ attrib1 /'の代わりに '$ 1 ==" _ attrib1 "'のような条件を作ることもできますし、 '$ 1〜/^_ attrib1 $/'私は最初の代替ソリューションをお勧めします。常に最初の文字列マッチング、正規表現(少なくとも)秒を選択します。 – ghoti

+0

新しい要件ごとに私の答えを更新しました。また、あなたの読書の喜びのために 'sed'の選択肢を追加しました。 – ghoti

1

これは動作するはずです:

#!/bin/bash 

awk 'BEGIN {FS="\t"} {if ($1=="_begin" || $1=="_attrib1") { output=output " " $2 }} END{print output}' 
関連する問題