awk 多重模式匹配并单行打印

awk 多重模式匹配并单行打印

我有以下文件:

$ cat disk.out
disk0
fcs0
text
text
text
disk1
fcs1
text
text
text
text
...

我想要实现的是匹配“disk”+“fcs”,然后在一行中打印这一对,如下所示:

disk0,fcs0
disk1,fcs1
...

所以我将“disk”和“fcs”匹配并将awk输出记录分隔符更改为“,”。`

$ awk '/disk|fcs/' ORS="," disk.out
disk0,fcs0,disk1,fcs1,

问题是,它会将所有匹配打印在一行上,并带有尾随,.如何在一行中仅打印每场比赛?像这样:

disk0,fcs0
disk1,fcs1
...

答案1

您必须保存“disk”行(不打印它),直到找到下一个“fcs”行:

awk '/disk/{ DISK=$0; next } /fcs/{ print DISK "," $0 }'

你的方法的问题是它打印任何一个匹配“disk”或“fcs”的行,不带结合那些行。

编辑:sp asic的脚本更稳健,因为它忽略了

disk3
text
fcs3

在这种情况下,我的脚本会很乐意打印“disk3,fcs3”。

答案2

$ awk '/fcs/ && a ~ /disk/ {print a","$0} {a=$0}' disk.out
disk0,fcs0
disk1,fcs1

string ~ /regexp/将检查正则表达式(此处)是否与给定字符串匹配,在本例中disk该字符串是可变的。这里使用a运算&&符来组合两个条件,只有第一个条件/fcs/和第二个条件a ~ /disk/都为真时,才会执行打印。

答案3

如果它始终采用这种格式(一个磁盘一个 fcs,fcs 始终在磁盘之后),您可以不用awk

grep -F -e disk -e fcs file | paste -d , - -

或者:

awk '(/disk/ && ORS=",") || (/fcs/ && ORS=RS)' file

尽管使用awk,您可能更喜欢 Martin 或 sp asic 给出的更清晰的方法。

相关内容