2016-06-14 26 views
1

线我用获得两个从壳

cmd | egrep 'ID|Value' 

andget我的命令行下面的输出:

ID: 2 
Value: 21 
    ID: 1 
Value: 25 
    ID: 1 
Value: 22 
    ID: 3 
Value: 56 
    ID: 1 
Value: 23 
    ID: 2 
Value: 50 
    ID: 2 
Value: 56 
    ID: 3 
Value: 11 
    ID: 3 
Value: 26 

我想通过一个特殊的ID进行过滤。但是当我使用:

egrep 'ID: 1|Value' 

它会显示相同的输出只有ID 1,但所有ID的值。

我已经阅读过关于awk,sed和regex的内容,但是我找不到能够真正帮助我的任何东西,但我也没那么深入。

有人可以提出一个想法,或告诉我,这是一个错误的方法来处理它,我应该以不同的方式做,如何?

输出通缉:

ID: 1 
Value: 25 
    ID: 1 
Value: 22 
    ID: 1 
Value: 23 
+0

所以你想要显示包含'ID:1'的块以及包含'Value:25'的以下行吗? – fedorqui

+0

我添加了我想要的输出 – DaPole

回答

8

只要告诉grep与下一个一起打印匹配行:

$ grep -A1 'ID: 1$' file 
    ID: 1 
Value: 25 
    ID: 1 
Value: 22 
-- 
    ID: 1 
Value: 23 

man grep

-A NUM, --after-context = NUM​​

在匹配行后打印尾行上下文的NUM行。 在 连续的匹配组之间放置一个包含组分隔符( - )的行。使用-o或 - 仅匹配的 选项,这不起作用并给出警告。

请注意使用$来标记行结束。否则,这将匹配线路ID: 1323423423

如果你不喜欢--出现在比赛之间,摆脱它具有:

grep -A1 --no-group-separator 'ID: 1$' file 
#  ^^^^^^^^^^^^^^^^^^^^ 
+0

是的,这应该就够了。 – Alan

+2

请注意,-A1的意思是“之后”,如果你想要的行之前,你可以使用-B1(“之前” – Alan

+2

@Alan准确。如果你的“之后”和“之前”匹配,你可以加入他们使用'-C – fedorqui

5

使用awk

awk '/ID: 1/{line[NR]; line[NR+1]}; NR in line' file 

会给作为输出的另一种简单的脚本: -

ID: 1 
Value: 25 
    ID: 1 
Value: 22 
    ID: 1 
Value: 23 

NR是一个特殊的awk存储记录号码的变量。我们所做的只是匹配一个模式,并获取要在文件中打印的行中的NthN+1th记录,并确保要打印的记录完全位于该行的最大范围内(NR in line)。

+1

这是我第一次看到'NR' ... +1这种用于创造力的用途。希望我会记住它...... – anishsane

6

对于其它标签:

AWK

awk '/ID: 1$/ {print; getline; print}' 

SED,非常相似

sed -n '/ID: 1$/ {p;n;p}' 

和bash

while read line; do if [[ $line == *"ID: 1" ]]; then echo "$line"; read line; echo "$line"; fi; done 
+2

这就是不切割和粘贴的问题。 –

1

使用GNU sed(有时可用的溶液如gsed BSD系统):

$ sed -n -e '/ID: 1/,+1p' data.in 
    ID: 1 
Value: 25 
    ID: 1 
Value: 22 
    ID: 1 
Value: 23 

说明:sed脚本“/ID: 1/,+1p”上在范围/ID: 1/+1输入的所有行施加p(打印)指令,即,每一行指定正则表达式“ ID: 1“和”沿着一条线“(+n地址是POSIX标准的GNU扩展)。

-n标志为sed可确保只打印p命令打印的内容(“禁止自动打印图案空间”)。

0

这可能为你工作(GNU SED):

sed '/ID: 1$/!d;n' file 

删除任何行不ID: 1,然后打印出来下。