有一个包含
等内容的文件2016-03-24 22:10:05,399 INFO aa
2016-03-24 22:10:05,399 INFO bb
2016-03-24 22:10:06,903 INFO cc
2016-03-24 22:10:07,804 INFO dd
2016-03-24 22:10:07,904 INFO ee
2016-03-24 22:10:05,399 INFO ff
2016-03-24 22:10:05,399 INFO gg
我想删除具有相同开头的行(INFO blab-bla-bla...
之前的部分)。
我可以使用像Ruby这样的全功能编程语言来执行它,但由于文件大小和其他一些原因我想使用sed
。
预期结果:
2016-03-24 22:10:05,399 INFO aa
2016-03-24 22:10:06,903 INFO cc
2016-03-24 22:10:07,804 INFO dd
2016-03-24 22:10:07,904 INFO ee
2016-03-24 22:10:05,399 INFO ff
过去为了删除相同的行,我使用了命令
sed'$!N; /^(.*)\n\1$/!P; d'
如果我理解正确的话,读取输入行,然后将下一行的\ n(如果它不是最后一行)附加到模式空间,然后,如果有一个序列,如“从开头到\的任何行” n加上相同的行直到行结束“,打印第二行并删除它。
我试图使用上面提到的一个更复杂的sed命令但没有成功,至少剩下一个逻辑块:
cat temp.log | sed '$!N; s/ INFO.*//; /^\(.*\)\n\1$/!P; D'
我想要做的是从当前行中删除以INFO
开头的所有内容,然后附加下一行,
2016-03-24 22:10:05,399
2016-03-24 22:10:05,399 INFO bb
删除以INFO
开头的所有内容,
2016-03-24 22:10:05,399
2016-03-24 22:10:05,399
然后删除第二行,如果它们相同的话。如何替换下一行?我使用\1
和&
尝试了几项但没有效果。
答案 0 :(得分:2)
根据我对您的问题的理解,这是另一个可能的awk
脚本:
awk -F"[, ]" 'prev!=$3; {prev=$3}' file
它将基于与前一行具有相同值的第3个元素去除所有行。
答案 1 :(得分:1)
命令:
awk -F" INFO " 'seen[$1]==0{print; seen[$1]++;next} seen[$1]==1{seen[$1]=0}' sample.csv
使用"信息"作为字段分隔符并将第一个字段存储到数组seen
中,第一个字段是INFO之前的日期时间。如果日期时间不在数组中,则看到[$ 1]返回false,!
将使其成立。 ++
是递增运算符,它会增加发生时间
seen[$1]==1{seen[$1]=0}
将值重置为0
答案 2 :(得分:1)
这是uniq
的工作。通过仅比较前23个字符(日期和时间),以下简单行将完全符合您的要求:
$ uniq -w 23 temp.log
答案 3 :(得分:1)
这是一个非正统的解决方案......
$ rev file | uniq -f2 | rev
2016-03-24 22:10:05,399 INFO aa
2016-03-24 22:10:06,903 INFO cc
2016-03-24 22:10:07,804 INFO dd
2016-03-24 22:10:07,904 INFO ee
2016-03-24 22:10:05,399 INFO ff
答案 4 :(得分:1)
sed用于单个行上的简单替换,即全部。如果你使用s,g和p以外的sed命令(和-n)那么你使用了错误的工具,因为所有其他的sed结构在1970年代中期发明awk时已经过时了。
$ awk '{c=$1$2} p!=c; {p=c}' file
2016-03-24 22:10:05,399 INFO aa
2016-03-24 22:10:06,903 INFO cc
2016-03-24 22:10:07,804 INFO dd
2016-03-24 22:10:07,904 INFO ee
2016-03-24 22:10:05,399 INFO ff