是否可以通过一个命令处理多行grep输出?
我有类似
的东西<fulldata>
<value>1</value>
<value>2</value>
</fulldata>
<fulldata>
<value>2</value>
<value>3</value>
</fulldata>
并希望得到资产,标准偏差并自行处理数据元素。
在这种情况下,我想执行
function printStatistics {
mean1=$(awk -F ';' '{print $1}' $1 | awk '{sum += $1; square += $1^2} END {print sum / NR}')
deviation1=$(awk -F ';' '{print $1}' $1 | awk '{sum += $1; square += $1^2} END {print sqrt(square / NR - (sum/NR)^2)}')
size=$(cat $1 | wc -l)
echo $mean1 $deviation1 $size
}
具有预期结果(对于样本数据),理想情况下由换行符分隔:
1,5 0,7 2
2,5 0,7 2
运行
cat add.xml | grep "<fulldata" -A 2001 | while read line ; do echo "Line: $line" ; done
像How to grep and execute a command (for every match)中建议的那样,确实会为每一行产生一个条目;但我希望每个条目都有一个条目(以便稍后在其上执行awk
个内容。)
这对grep是否可行,或者这是另一种语言更合适的用例?
答案 0 :(得分:1)
使用grep解析html / xml是不好的做法,因为它不可靠。如果您使用的是Mac OS X,则可以使用名为xmllint
的预安装cli工具来选择特定元素。在linux上,您可以使用标准包管理器来获取它。
还有xgrep,还有其他我不知道的事情。
答案 1 :(得分:1)
awk
救援!
$ awk -v RS='\n?</?fulldata>\n' -F'\n' '
!(NR%2){gsub("</?value>","");
s=ss=0;
for(i=1;i<=NF;i++) {s+=$i; ss+=$i^2}
printf "%.1f %.1f %d\n", s/NF, sqrt((ss-s^2/NF)/(NF-1)), NF} ' file
1.5 0.7 2
2.5 0.7 2
对于计算的样本标准差,您需要保护单个观察(NF == 1)的情况。
答案 2 :(得分:1)
复杂xmlstarlet
+ awk
解决方案:
xmlstarlet ed -u "//fulldata/value" -x "concat(.,',')" add.xml \
| xmlstarlet sel -B -t -v "//fulldata" -n \
| awk -F, '{ n=NF-1; sum=sq=0; for(i=1;i<=n;i++) { sum+=$i; sq+=$i^2 }
printf "%.1f\n%.1f\n%d\n", sum/n, sqrt((sq-sum^2/n)/(n-1)), n }'
输出:
1.5
0.7
2
2.5
0.7
2