はじめに
awkはテキスト処理に特化した強力なコマンドであり、ログ解析やデータ整形などで広く利用されています。
その中でもvariableの扱いは、処理の柔軟性や効率を大きく左右する重要な要素です。
しかし、初学者にとっては「どこで宣言するのか」「型はどう扱われるのか」など、つまずきやすいポイントが多いのも事実です。
本記事を読むことでawkを単なるワンライナーから一歩進んだ実用的なツールとして活用できるようになります。
参考:GNU awk
AWKにおける変数の基本概念と宣言のルール
ファイル作成
cat << 'EOF' > input.txt
apple 100
banana 200
orange 300
EOF
実行コマンド
awk '{ total += $2 } END { print total }' input.txt
実行結果
600
実行コマンド
awk '{ count++; sum += $2 } END { print "avg=" sum/count }' input.txt
実行結果
avg=200
仕組み
| 要素 | 内容 | ポイント |
|---|---|---|
| total | 合計値を保持する変数 | 初期化なしで0から開始 |
| count | 行数カウント用の変数 | 使用時に自動生成される |
| $2 | 2列目のフィールド | 数値として扱われる |
| += | 加算代入 | total = total + $2 と同義 |
| END | 入力処理後に実行されるブロック | 集計結果を出力する用途 |
解説
awkの変数は宣言不要で初期値0または空文字から自動生成されるため、シンプルに集計処理を書けるのが特徴です。
コマンドライン引数から変数を渡す -v オプションの活用法
ファイル作成
cat << 'EOF' > input.txt
apple 100
banana 200
orange 300
EOF
実行コマンド
awk -v threshold=150 '$2 > threshold {print $1, $2}' input.txt
実行結果
banana 200
orange 300
仕組み
| 要素 | 内容 | 説明 |
|---|---|---|
| -v threshold=150 | awk変数の定義 | シェルからawkへ変数を渡す |
| $2 > threshold | 条件式 | 2列目の数値がthresholdより大きい行を抽出 |
| {print $1, $2} | アクション | 条件に一致した行の1列目と2列目を出力 |
| input.txt | 入力ファイル | 処理対象データ |
解説
-vオプションを使うことで、シェル側の値をawk内で柔軟に利用できます。
条件を外部から変更できるため、スクリプトの再利用性が高まります。
BEGINブロックを利用した変数の初期化と効率化
ファイル作成
cat << 'EOF' > input.txt
apple 100
banana 200
orange 150
EOF
実行コマンド
awk 'BEGIN { total=0 } { total += $2 } END { print total }' input.txt
実行結果
450
仕組み
| ブロック | タイミング | 内容 | 役割 |
|---|---|---|---|
| BEGIN | 処理開始前 | total=0 | 変数の初期化(効率的に1回のみ実行) |
| メイン処理 | 各行ごと | total += $2 | 2列目の数値を加算 |
| END | 処理終了後 | print total | 集計結果の出力 |
解説
BEGINブロックで変数を初期化することで無駄な再初期化を防ぎ効率化できる。awkの変数は自動生成されるが、明示的に管理すると可読性も向上する。
組み込み変数(NR, NF, FS, RS)とユーザー定義変数の使い分け
ファイル作成
cat << 'EOF' > input.txt
apple 100 red
banana 200 yellow
grape 300 purple
EOF
実行コマンド
awk '{ print "NR=" NR, "NF=" NF, $0 }' input.txt
実行結果
NR=1 NF=3 apple 100 red
NR=2 NF=3 banana 200 yellow
NR=3 NF=3 grape 300 purple
実行コマンド
awk 'BEGIN { FS=" " } { print $1, $2 }' input.txt
実行結果
apple 100
banana 200
grape 300
実行コマンド
awk '{ total += $2 } END { print "Total=" total }' input.txt
実行結果
Total=600
実行コマンド
awk 'BEGIN { RS="\n" } { print NR ":" $0 }' input.txt
実行結果
1:apple 100 red
2:banana 200 yellow
3:grape 300 purple
仕組み
| 種類 | 変数名 | 役割 | 例 |
|---|---|---|---|
| 組み込み変数 | NR | レコード番号 | 行番号の取得 |
| 組み込み変数 | NF | フィールド数 | 列数の取得 |
| 組み込み変数 | FS | フィールド区切り | 空白やカンマで分割 |
| 組み込み変数 | RS | レコード区切り | 改行や任意文字で区切り |
| ユーザー定義変数 | total | 任意の値を保持 | 合計値の計算 |
解説
awkの組み込み変数は入力データの構造を扱うためのもので、ユーザー定義変数は計算や状態保持に使う。
役割を分けることで可読性と柔軟性が向上する。
環境変数をAWKスクリプト内で参照する方法(ENVIRON配列)
ファイル作成
cat << 'EOF' > input.txt
apple 100
banana 200
EOF
実行コマンド
export RATE=1.1
awk '{ price = $2 * ENVIRON["RATE"]; print $1, price }' input.txt
実行結果
apple 110
banana 220
仕組み
| 要素 | 内容 | 例 |
|---|---|---|
| ENVIRON配列 | awk内で環境変数を参照する仕組み | ENVIRON["RATE"] |
| export | 環境変数をシェルに設定 | export RATE=1.1 |
| $1, $2 | 入力行のフィールド参照 | apple, 100 |
| 演算 | awk内で計算可能 | $2 * ENVIRON["RATE"] |
| 結果の出力 | print $1, price |
解説
awkではENVIRON配列を使うことで、シェルの環境変数をそのまま参照できます。これにより、スクリプトを変更せず外部から値を柔軟に切り替えられます。
数値と文字列の自動型変換における注意点
ファイル作成
cat << 'EOF' > input.txt
10 apple
20 banana
30 cherry
EOF
実行コマンド
awk '{ total += $1; text += $2 } END { print total, text }' input.txt
実行結果
60 0
実行コマンド
awk '{ total += $1; text = text $2 } END { print total, text }' input.txt
実行結果
60 applebananacherry
仕組み
| 要素 | 挙動 | 注意点 |
|---|---|---|
| total += $1 | 数値として加算 | 正常に数値合計される |
| text += $2 | 数値として加算しようとする | 文字列は0に変換される |
| text = text $2 | 文字列連結 | 期待通り文字列として結合される |
| awk variable | 型を明示せず自動判定 | 文脈によって数値/文字列が切り替わる |
解説
awkの変数は文脈によって数値にも文字列にもなるため、+=を使うと意図せず数値変換されます。文字列操作では明示的に連結(text = text $2)を使うのが安全です。
算術演算子と代入演算子を用いた変数の更新処理
ファイル作成
cat << 'EOF' > input.txt
10
20
30
EOF
実行コマンド
awk '{ sum += $1; print "現在の合計:", sum }' input.txt
実行結果
現在の合計: 10
現在の合計: 30
現在の合計: 60
実行コマンド
awk '{ product *= ($1==""?1:$1); if(NR==1) product=$1; print "現在の積:", product }' input.txt
実行結果
現在の積: 10
現在の積: 200
現在の積: 6000
仕組み
| 要素 | 内容 | 説明 |
|---|---|---|
| sum += $1 | 加算代入 | 変数sumに現在の値を加算 |
| product *= $1 | 乗算代入 | 変数productに値を掛ける |
| $1 | フィールド参照 | 各行の1列目の値 |
| NR | レコード番号 | 行番号(初期化判定に使用) |
| 変数 | awk内で自動生成 | 初期値は0または未定義 |
解説
awkでは変数が自動生成され、+=や*=などの演算子で逐次更新できます。
ループ不要でストリーム処理的に計算できるのが強みです。
条件分岐(if)とループ(for|while)内での動的な変数操作
ファイル作成
cat << 'EOF' > input.txt
apple 10
banana 20
orange 30
EOF
実行コマンド
awk '{
total += $2
if ($2 > 15) {
count++
}
}
END {
for (i = 1; i <= count; i++) {
printf "loop %d\n", i
}
print "total =", total
}' input.txt
実行結果
loop 1
loop 2
total = 60
仕組み
| 要素 | 内容 | 説明 |
|---|---|---|
| $2 | 数値フィールド | 各行の2列目を取得 |
| total += $2 | 変数加算 | 行ごとに合計値を更新 |
| if ($2 > 15) | 条件分岐 | 15より大きい値のみ処理 |
| count++ | カウンタ増加 | 条件成立時に加算 |
| END | 後処理ブロック | 全行処理後に実行 |
| for | ループ | count回だけ繰り返し |
解説
awkではレコード処理中に変数を動的更新し、ENDブロックでまとめて利用できる。
ifとforを組み合わせることで柔軟な集計と制御が可能。
連想配列(Map)を変数として活用したデータの集計手法
ファイル作成
cat << 'EOF' > input.txt
apple 100
banana 200
apple 150
orange 300
banana 50
EOF
実行コマンド
awk '{ sum[$1] += $2 } END { for (k in sum) print k, sum[k] }' input.txt
実行結果
apple 250
banana 250
orange 300
仕組み
| 要素 | 内容 |
|---|---|
| キー | $1(商品名) |
| 値 | $2(数値データ) |
| 連想配列 | sum[key] += value |
| 集計タイミング | 各行処理時に加算 |
| 出力処理 | ENDブロックで全キーをループ出力 |
解説
awkの変数は連想配列として動的にキーを生成でき、カテゴリ別集計に非常に有効です。シンプルな構文でグルーピングと集計を同時に実現できます。
外部ファイルから変数に値を読み込む getline 関数
ファイル作成
cat << 'EOF' > input.txt
apple 100
banana 200
cherry 300
EOF
実行コマンド
awk 'BEGIN { getline line < "input.txt"; split(line, a, " "); val=a[2] } { print $1, val }' input.txt
実行結果
apple 100
banana 100
cherry 100
仕組み
| 要素 | 内容 |
|---|---|
| getline line < "input.txt" | 外部ファイルから1行読み込み変数lineへ格納 |
| split(line, a, " ") | 読み込んだ行をスペースで分割し配列aへ |
| a[2] | 2番目の要素(ここでは100)を取得 |
| val=a[2] | awk内変数valへ代入 |
| { print $1, val } | 各行の1列目と固定値valを出力 |
解説
getlineを使うことで、処理対象とは別のファイルから値を取得し変数として利用できます。これにより外部データを柔軟に組み込めます。
関数内ローカル変数とグローバル変数の管理
ファイル作成
cat << 'EOF' > input.txt
apple 10
banana 20
apple 30
banana 40
EOF
実行コマンド
awk '{ total[$1] += $2; sum += $2 } END { for (k in total) print k, total[k]; print "GLOBAL_SUM", sum }' input.txt
実行結果
apple 40
banana 60
GLOBAL_SUM 100
仕組み
| 種類 | 変数名 | スコープ | 説明 |
|---|---|---|---|
| ローカル風(キー別管理) | total[$1] | 連想配列(擬似ローカル) | キーごとに値を保持(apple, banana単位) |
| グローバル | sum | 全体共有 | 全レコードの合計値を保持 |
| 入力フィールド | $1, $2 | 行単位 | 各行のデータ参照 |
| ENDブロック | - | 全体後処理 | 集計結果の出力 |
解説
awkでは関数スコープは弱く、配列でキー管理することで“ローカル的”な振る舞いを実現する。単一変数は全体で共有されるグローバルとして動作する。
デバッグ効率を上げるための変数値の出力
ファイル作成
cat << 'EOF' > input.txt
apple 100
banana 200
orange 300
EOF
実行コマンド
awk '{ total += $2; print "DEBUG: item=" $1 ", price=" $2 ", total=" total } END { print "SUM=" total }' input.txt
実行結果
DEBUG: item=apple, price=100, total=100
DEBUG: item=banana, price=200, total=300
DEBUG: item=orange, price=300, total=600
SUM=600
仕組み
| 要素 | 内容 |
|---|---|
| $1 | 1列目(商品名) |
| $2 | 2列目(数値) |
| total | awk内で定義された変数(累積用) |
| total += $2 | 値を加算しながら保持 |
| デバッグ用に変数内容を逐次出力 | |
| END | 全行処理後に最終結果を出力 |
解説
awkでは変数を自由に使えるため、printで途中経過を出力するとデバッグ効率が上がります。
特に累積処理や条件分岐の確認に有効です。
変数を使ったログファイルの集計とレポート生成
ファイル作成
cat << 'EOF' > input.txt
2026-05-01 INFO 120
2026-05-01 ERROR 30
2026-05-02 INFO 200
2026-05-02 ERROR 50
2026-05-03 INFO 150
2026-05-03 ERROR 20
EOF
実行コマンド
awk '{ count[$2] += $3 } END { for (level in count) print level, count[level] }' input.txt
実行結果
INFO 470
ERROR 100
実行コマンド
awk -v threshold=100 '{ count[$2] += $3 } END { for (level in count) if (count[level] > threshold) print level, count[level] }' input.txt
実行結果
INFO 470
仕組み
| 要素 | 内容 |
|---|---|
| $2 | ログレベル(INFO / ERROR) |
| $3 | 数値データ(件数やサイズ) |
| count[$2] += $3 | レベルごとに合計を集計 |
| -v threshold=100 | awk内で使う変数を外部から定義 |
| END | 全行処理後に結果を出力 |
| for (level in count) | 配列の全キーをループ |
解説
awkの変数と連想配列を使うことで、ログレベル別の集計や条件付きレポートが簡潔に実現できます。-vオプションにより柔軟な条件設定も可能です。
awkのvariableを自在に扱うためのポイントまとめ
awkにおけるvariableは、単なる値の入れ物ではなく、処理の流れをコントロールする中心的な役割を担います。
基本的には宣言不要で使える点が特徴ですが、その分スコープや初期化のタイミングを意識しないと予期しない挙動につながります。
awkとvariableを正しく理解し、小さな処理から積み重ねていくことがスキル向上への近道です。

![[sed] 実行して理解 指定した範囲の行を削除 文字列のsed](https://running-terminal-commands.com/wp-content/uploads/thumbnail_sed_1920_1080.png.webp)