有选择地在一个术语上使用'grep --after-context'而不是另一个术语

时间:2013-07-26 11:26:25

标签: shell unix sed awk grep

我从网络中提取大量数据并过滤foobar,例如

for i in example.com example.org example.net
do
     echo "Data from $i"
     curl $i/data.csv | grep --after-context=3 "foo|bar"
done

每次出现foo时,我都需要看到接下来的几行(grep --after-context=3),但是当bar出现时,我只需要那一行。

是否可以在单grepsedawk(或其他标准unix)命令中使用它?

3 个答案:

答案 0 :(得分:4)

一种方式:

curl .... | awk  '/foo/{x=NR+3}(NR<=x) || /bar/'

当遇到foo时,x被设置为当前行号+3,因此条件(NR+x)使行“foo”并且接下来的3行被打印。 /bar/使包含bar的行打印出来。

答案 1 :(得分:1)

awk 'BEGIN {np=0} /bar/ {print; next} /foo/ {np=1;ln=RN;print;next} ln!=0 && RN>(ln+3) {np=0;ln=0} np==1 {print}' INPUTFILE

您可以使用以上内容代替grep。它的作用:

  1. BEGIN中设置非打印变量。
  2. /bar/ {print}如果你无法解决这个问题,那么......(next用于跳过所有其他规则并转到下一条记录)。
  3. /foo/ {np=1;ln=RN;print}打印foo行,保存行号,然后设置打印后续行
  4. 如果实际行号大于保存的行号加3,则将打印设置为关闭
  5. 如果我们需要打印(np>0),请打印。

答案 2 :(得分:1)

这可能适合你(GNU sed);

sed -n '/foo/,+3{p;b};/bar/p' file