在perlrun 实战1 中我们提到了可以使用下面的命令来得到Query Type的平均执行时间:
cat logfile | perl -ne ‘/[QueryType=([^]]+).+[TimeCost=([d.]+)ms/; $QT{$1} +=$2; $CNT{$1}++; END {for $key (keys(%QT)) {print $key, ": ", $QT{$key}/$CNT{$key},"n" } }’ | sort
这里使用了END,我们再来看这样一个需求。我们要得到每种QueryType的时间消耗的分布:
-bash-3.00$ cat logfile | perl -lne ‘$total += $2; $time{$1} += $2 if /[QueryType=([^]]+).+[TimeCost=([d.]+)ms/ } { $time{$_} /= $total for keys %time; printf "%02d%%t%sn", 100*$time{$_}, $_ for keys %time’ | sort -rn | head -10
31% Type1
08% Type2
07% Type3
05% Type4
04% Type5
注意我用红色标出的一对大括号。在Perlrun实战[1] 中介绍了使用-n的时候,perl会把我们输入的代码放在一对大括号中。我们使用-MO=Deparse看一下:
-bash-3.00$ perl -MO=Deparse -ne ‘ ‘
LINE: while (defined($_ = <ARGV>)) {
();
}
注意到蓝色的那对大括号是perl自动帮我们加上的。
-bash-3.00$ perl -MO=Deparse -ne ‘ }{ ‘
LINE: while (defined($_ = <ARGV>)) {
();
}
{ ;} ;
注意到,当我在”中插入了一对}{ 后,其实perl是很机械得做了替换,于是我成功我插入的右括号和perl生成的左括号配对,我插入的左括号和perl生成的右括号配对。
于是上面的统计时间分布的代码变成:
LINE: while (defined($_ = <ARGV>)) {
chomp $_;
$total += $2;
$time{$1} += $2 if /[QueryType=([^]]+).+[TimeCost=([d.]+)ms/;
}
{
foreach $_ (keys %time) {
$time{$_} /= $total;
}
foreach $_ (keys %time) {
printf "%02d%%t%sn", 100 * $time{$_}, $_;
}
}
sort -rn 表示按照数字的大小(-n)进行从大到小(-r)的排序。