AWK覚え書き(3)

二重出力、またはパターンの解決について

事象

hello.datの時はフィールド1の先頭に"hello!"って付けて、それ以外のファイルはそのまま出力させようとして、下記のようなプログラムを組んだんですが失敗。

hello.awk

FILENAME ~ /hello[[:digit:]]*\.dat/ {
  $1 = "hello!" $1
  print
}

{
  print
}

hello.dat

abcde
fghij
# awk -f hello.awk hello.dat
hello!abcde
hello!abcde
hello!fghij
hello!fghij
原因

空パターンは、全ての入力レコードとマッチするように扱われる。
たとえ他のパターンが該当するとしても。

パターンをIF ... ELSE IF... ELSE ... みたいなものと考えていたんですがそうではなく、該当するパターンは全て実行されるようです。

CASE文のbreakと同様の処理として、nextがあります。The GNU Awk User's Guide - アクション中の制御文参照。

対策

空パターンでのみprintを実行するように修正。

# awk -f hello.awk hello.dat
hello!abcde
hello!fghij
補足1

空パターンを先頭に持っていくと挙動が変わる → 先頭から順に解決
2008-11-23追記:コメントにより確定したので?取りました

# awk -f hello.awk hello.dat
abcde
fghij