我可以 grep/awk/sed 一行中的多个匹配项并获取其后的信息吗?

我可以 grep/awk/sed 一行中的多个匹配项并获取其后的信息吗?

我收到的文件来自外部源,这些文件是无序的......并且包含一些我感兴趣的信息和一些我不感兴趣的信息。

name: myName var1: xxx var2: bbbb
var1: xxx var2: aaaa name: myName
name: myName var1: yyy var2: bbbb
var1: xxx var2: aaaa name: myName
name: myName var1: yyy var2: aaaa
var2: aaaa name: myName var1: xxx 
name: myName var1: zzz var2: bbbb
var2: aaaa name: myName var1: zzz

我想要输出的只是与var1和相关的值,var2并且已排序,因此这var1是第一个。就像这样:

xxx bbbb
xxx aaaa
yyy bbbb
xxx aaaa
yyy aaaa
xxx aaaa
zzz bbbb
zzz aaaa

如果这可能的话有什么想法吗?

答案1

你可以这样做awk

awk '{
        v1 = v2 = ""
        for (i=1; i<NF; i+=2) {
                if ($i == "var1:") v1 = $(i+1)
                if ($i == "var2:") v2 = $(i+1)
        }
        print v1, v2
     }'

对于每一行,它测试所有奇数字段($1$3和 $5)是否为var1:或 var2:,如果匹配,则将值(从下一个字段 ,$(i+1)变为$2$4或 $6)复制到v1或 v2

答案2

在 Perl 中,从键值对创建哈希:

$ perl -alnE 'my %h = @F; say "$h{qw(var1:)} $h{qw(var2:)}"' file
xxx bbbb
xxx aaaa
yyy bbbb
xxx aaaa
yyy aaaa
xxx aaaa
zzz bbbb
zzz aaaa

答案3

您可以通过多种方式完成此操作,其中两种方式如下所示:

$ perl -lne 'print /(?=.*var1:\h+(\H+))(?=.*var2:(\h+\H+))/' input.file


$ sed -e '
     H;s/.*//;x
     s/.*[[:space:]]var2: \([^[:space:]]\{1,\}\)/\1 &/
     s/.*[[:space:]]var1: \([^[:space:]]\{1,\}\)/\1 &/
     s/ \n.*//
' input.file

有了 中的功能GNU sed,我们可以简化很多:

$ sed -Ee ' 
    s/^/\n/
    s/.*\svar2: (\S+)/\1 &/
    s/.*\svar1: (\S+)/\1 &/
    s/ \n.*//
' input.file

输出:

xxx bbbb
xxx aaaa
yyy bbbb
xxx aaaa
yyy aaaa
xxx aaaa
zzz bbbb
zzz aaaa

答案4

dat 中的数据,使用 gnu sed;

$ sed -E 's/.*var1:\s(\S+).+var2:\s(\S+).*|.*var2:\s(\S+).+var1:\s(\S+).*/\1\4 \2\3/' dat

相关内容