するとき:
for i in {1..30}; do echo $i; grep $i/Aug access.log | sort -u | wc -l; done;
問題は、次のように進むことです。
1/Aug # should be 01/Aug
2/Aug # should be 02/Aug
...
for i in {1..30}
1、2、3の代わりに01、02、03を提供する方法は?
答え1
bash
と ではzsh
次のように使用します{01..30}
。
$ for i in {01..30}; do
echo $i
# other code using "$i"
done
01
02
03
04
05
06
(etc.)
ksh93
を使用しています{0..30%02d}
。
sh
または、他のPOSIXシェルで次のものを使用してください。
i=0
while [ "$(( i += 1 ))" -le 30 ]; do
zi=$( printf '%02d' "$i" )
echo "$zi"
# other code using "$zi"
done
変数i
も引用符で囲む必要があります。
for i in {01..30}; do
echo "$i"
grep "$i/Aug" access.log | sort -u | wc -l
done
または、
sed -E -n 's#^.*([0-9][0-9]/Aug).*$#\1#p' access.log | sort | uniq -c
または
grep -o '[0-9][0-9]/Aug' access.log | sort | uniq -c
この単一パイプライン(ループなし)は、一致する日付2-digit-number/Aug
とその日付文字列に一致するアクセスログエントリの数を出力します。
[0-9][0-9]/Aug
これは、ファイルから発生したすべての項目を抽出してソートし、各発生回数を計算する方法でuniq
行われます。
このgrep
バリアントはsed
コマンドよりも見やすくなりますが、大きすぎる数値を提供します。もし日付文字列は1行に複数回表示されます。