順番に並んでいないIPアドレスの長いリストがあります。特定のIPアドレスの前後にIPアドレスがいくつあるかを調べる必要があります。どうすればこれを達成できますか?
順番に並んでいないIPアドレスの長いリストがあります。特定のIPアドレスの前後にIPアドレスがいくつあるかを調べる必要があります。どうすればこれを達成できますか?
回答:
多分最も簡単なのは、
sed -n '/pattern/{=; q;}' file
エラーを指摘してくれた@JoshepRに感謝
dc
おそらくこれを直接、私自身に直接パイプします。
私はこれを2つの方法で行いましたが、これが一番好きだと思います。
: $(( afterl=( lastl=$(wc -l <~/file) ) - 2 -
$(( beforel=( matchl=$(sed -n "/$IP/{=;q;}" <~/file) ) - 1
)) ))
for n in last match afters befores
do printf '%s line%s :\t%d\n' \
"${n%s}" "${n##*[!s]}" $((${n%s}l))
done
これにより、それらすべてが現在のシェル変数として保存され、その後forループで評価されて出力されます。ファイル内の合計行数をカウントしwc
、で最初に一致した行番号を取得しsed
ます。
その出力:
last line : 1000
match line : 200
after lines : 799
before lines : 199
私もしました:
sed -n "/$IP/=;\$=" ~/file |
tr \\n \ | {
IFS=' ' read ml ll
printf '%s line%s:\t%d\n' \
last '' $((ll=${ll##* }))
match '' $ml \
after s "$((al=ll-ml-1)) \
before s $((bl=ml-1))
}
sed
一致する最後の行番号のみを出力しtr
、間にある\n
ewlinesを次のように変換します。、とread
の最初の読み込みsed
さんへの結果$ml
に、他のすべてを$ll
。複数の一致の可能性があるケースは、$ll
後で再度設定するときに、の展開から最後の結果を除いてすべてを取り除くことによって処理されます。
その出力:
last line : 1000
match line : 200
after lines : 799
before lines : 199
どちらの方法も、次の方法で生成されたファイルでテストされました。
IP='some string for which I seek'
for count in 1 2 3 4 5
do printf '%.199d%s\n' 0 "$IP"
done | tr 0 \\n >~/file
それは行番号で:
"$IP"
次に\n
ewlineを出力しますtr
-ゼロを\n
ewlineに変換し、次に~/file
これを行うPerlコードの一部を次に示します。
perl -ne '
if(1 .. /192\.168\.1\.1/) { $before++ }
else { $after++ }
$before--; # The matching line was counted
END{print "Before: $before, After: $after\n"}' your_file
これは、IPを含む行の前後の行の総数をカウントします192.168.1.1
。希望のIPに置き換えます。
Bashのみを使用:
before=0
match=0
after=0
while read line;do
if [ "$line" = 192.168.1.1 ];then
match=1
elif [ $match -eq 0 ];then
before=$(($before+1))
else
after=$(($after + 1))
fi
done < your_file
printf "Before: %d, After: %d\n" "$before" "$after"
$.
カウンターの代わりに使ってみませんか?
$after
するよりも読みやすいと思います$. - $before
。
$. - 1
に保存$.
し$tmp
ます。印刷を終了します$. - $tmp
。そのため、前後の両方にカウンターは必要ありません。もちろんそれはあなたのものよりも読みにくいです。
Grep
特定のパターンが見つかった回数をカウントできる機能があります。そうする-c
コマンドを使用する場合。-c
and -v
コマンドを使用すると、これが特定のパターンに一致しない回数がカウントされます
例:
grep -c -v <pattern> file
したがって、次のようなことを試した場合:
grep -c -v 192.168.x.x file.log
それはうまくいくはずです。