我有一个文件/tmp/log/1GPS_garmin2.log
,我想计算车辆第一次停车和最后一次停车之间经过了多少时间。
以下是数据示例:
181225.249849952:,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.254218266:$GPVTG,000.0,T,355.7,M,000.01,N,**0000**.02,K*79
181225.259072464:$GPRMC,161212.2,A,4653.89701,N,01940.55676,E,000.01,000.0,100913,004.3,E*59
181225.264592889:$GPGGA,**161212**.2,4653.89701,N,01940.55676,E,2,08,1.4,124.2,M,41.3,M,,*5C
181225.268283132:$GPGSA,A,3,,03,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.274272586:$GPVTG,000.0,T,355.7,M,000.01,N,0000.01,K*7A
181225.277401076:$GPRMC,161212.4,A,4653.89701,N,01940.55676,E,000.01,000.0,100913,004.3,E*5F
181225.280493945:$GPGGA,161212.4,4653.89701,N,01940.55676,E,2,08,1.4,124.2,M,41.3,M,,*5A
181225.283556186:$GPGSA,A,3,,03,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.286888004:$GPVTG,000.0,T,355.7,M,000.01,N,0000.01,K*7A
181225.290137581:$GPRMC,161212.6,A,4653.89701,N,01940.55677,E,000.01,000.0,100913,004.3,E*5C
181225.293265920:$GPGGA,161212.6,4653.89701,N,01940.55677,E,2,08,1.4,124.2,M,41.3,M,,*59
181225.297247457:$GPGSA,A,3,,03,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.300419979:$GPVTG,000.0,T,355.7,M,000.01,N,0000.02,K*79
181225.303577147:$GPRMC,161212.8,A,4653.89701,N,01940.55677,E,000.01,000.0,100913,004.3,E*52
181225.306632425:$GPGGA,161212.8,4653.89701,N,01940.55677,E,2,08,1.4,124.2,M,41.3,M,,*57
181225.310040084:$GPGSA,A,3,,03,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.313133946:$GPVTG,000.0,T,355.7,M,000.01,N,0000.01,K*7A
181225.317166965:$GPRMC,161213.0,A,4653.89701,N,01940.55677,E,000.01,000.0,100913,004.3,E*5B
181225.320426880:$GPGGA,161213.0,4653.89701,N,01940.55677,E,2,08,1.4,124.2,M,41.3,M,,*5E
181225.323792082:$GPGSA,A,3,,03,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.327003400:$GPVTG,000.0,T,355.7,M,000.01,N,0000.01,K*7A
181225.330192100:$GPRMC,161213.2,A,4653.89701,N,01940.55677,E,000.01,000.0,100913,004.3,E*59
181225.333141314:$GPGGA,161213.2,4653.89701,N,01940.55677,E,2,08,1.4,124.2,M,41.3,M,,*5C
181225.336206449:$GPGSA,A,3,,03,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.339610415:$GPVTG,000.0,T,355.7,M,000.01,N,0000.02,K*79
181225.342976480:$GPRMC,161213.4,A,4653.89701,N,01940.55678,E,000.01,000.0,100913,004.3,E*50
181225.346003737:$GPGGA,161213.4,4653.89701,N,01940.55678,E,2,08,1.4,124.2,M,41.3,M,,*55
181225.349040725:$GPGSA,A,3,,03,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.352282572:$GPVTG,000.0,T,355.7,M,000.01,N,0000.02,K*79
181225.355736225:$GPRMC,161213.6,A,4653.89700,N,01940.55678,E,000.01,000.0,100913,004.3,E*53
181225.359730217:$GPGGA,161213.6,4653.89700,N,01940.55678,E,2,08,1.4,124.2,M,41.3,M,,*56
181225.363299063:$GPGSA,A,3,,03,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.366588198:$GPVTG,000.0,T,355.7,M,000.01,N,0000.02,K*79
181225.371109954:$GPRMC,161213.8,A,4653.89700,N,01940.55678,E,000.01,000.0,100913,004.3,E*5D
181225.374346102:$GPGGA,161213.8,4653.89700,N,01940.55678,E,2,08,1.4,124.2,M,41.3,M,,*58
181225.377370616:$GPGSA,A,3,,03,06,,14,18,19,22,27,32,,,2.0,1.4,1.5*34
181225.380446435:$GPVTG,000.0,T,355.7,M,000.01,N,0000.02,K*79
该$GPVTG
行包含两个星号之间的车辆速度(文件中没有星号)。该$GPGGA
行包含时间,时间也位于两个星号之间。前两个字符是小时,接下来的两个字符是分钟,最后两个字符是秒。
当速度为 0000 时,车辆停止。我需要第一次和最后一次停止的时间,以便我可以将其更改为秒并写入log.txt
。
我可以进行更改和书写,但需要帮助来查找车辆首末站的时间。
这是我的 run.sh 文件:
#!/bin/bash
fullfilename=$1
filename=$(basename "$fullfilename")
ext="${filename##*.}"
if [[ $# -ne 1 ]]; then
echo "Error 1"
exit 1
elif [[ $ext != "log" ]]; then
echo "Error 2"
exit 1
elif [[ ! -r $fullfilename ]]; then
echo "Error 3"
exit 1
else
grep '$GPGGA' $1 > test1.txt
grep '$GPVTG' $1 > test2.txt
cut -c50-53 test2.txt > speed.txt
cat speed.txt | wc -l > dealer.txt
while read line
do
I=0; for N in $(cat speed.txt); do I=$(($I + 10#$N)); done;
echo "average speed:" $(($I / $line)) >> log.txt
done < dealer.txt
grep '0000' speed.txt | wc -l > stop.txt
while read stop
do
echo "number of stops:" $stop >> log.txt
done < stop.txt
fi
我已经计算了平均速度和停车次数。
awk
注意:我是 bash 的新手,所以我的解决方案不是最适合这项任务的,但是在我学会其他 bash 实用程序之前我不想使用它。
答案1
从您的样本来看:
$ sed -nr '/0000/N;N; s/.*GPGGA,([^,]+).*/\1/p' file | sed -n '1p;$p'
161212.2
161213.8
笔记
-n
在我们要求之前不要打印任何内容-r
使用 ERE/0000/N;N
找到一行0000
并阅读接下来的两行s/old/new
old
用。。。来代替new
.*
行中的任何字符([^,]+)
保存一些不在,
这个位置的字符\1
反向引用已保存的模式|
将输出传递给另一个sed
(不优雅的)'1p;$p'
打印第一行并打印最后一行
至于换算成秒数,就交给你了……
答案2
我会用awk
它来做类似的事情。
这个想法是将记录(行)拆分为逗号分隔的字段,然后:
- 如果第一个字段以 结尾
$GPVTG
,第八个字段以 开头0000
,则设置一个布尔标志来指示车辆已停止 - 当第一个字段结束
$GPGGA
且车辆停止时,保存第二个字段的距离值 - 最后,打印第一个和最后一个距离值
所以
#!/usr/bin/awk -f
function printsecs(s) {
print substr(s,5) + 60 * (substr(s,3,2) + 60 * substr(s,1,2));
}
BEGIN {FS=","}
$1 ~ /\$GPVTG$/ && $8 ~ /^0000/ {
stopped = 1;
}
$1 ~ /\$GPGGA$/ && stopped {
t[++n] = $2;
stopped = 0;
}
END {
printsecs(t[1]); printsecs(t[n]);
}