Denis Sheremet
Denis Sheremet

Reputation: 2583

Get all non-empty lines after the matched line

I've got a program which prints to stdout some data in the following format:

$ ./my_program
foo
line1
line2
line3

bar
line1

foo
line1
line2

baz
line1
line2

I want to filter it, so it only prints sets of non-empty lines starting with some matching string. Something like that:

$ ./my_program | grep -A* foo
foo
line1
line2
line3

foo
line1
line2

Unfortunately I can't just use stuff like -A2 or -A3 because number of lines may differ. Are there any built-in feature or a simple one-liner to do it?

Upvotes: 0

Views: 68

Answers (3)

Benjamin W.
Benjamin W.

Reputation: 52371

With sed:

./my_program | sed '/foo/,/^$/!d'

This deletes anything that is outside of the address range /foo/,/^$/ – lines between those matching foo and an empty line.

This works almost the same for awk, with the logic inverted (print if in range, instead of delete if not in range):

./my_program | awk '/foo/,/^$/'

Upvotes: 1

oguz ismail
oguz ismail

Reputation: 50795

With awk, read the file in paragraph mode, and print paragraphs matching ^foo.

$ awk 'BEGIN{RS="";ORS="\n\n"} /^foo/' file
foo
line1
line2
line3

foo
line1
line2

$

Upvotes: 3

steffen
steffen

Reputation: 17028

This should print the lines according to your description:

$ awk '/^$/{f=0}/foo/{f=1}f'
foo
line1
line2
line3
foo
line1
line2

This uses a flag (f) to indicate the search string was found. The flag is reset after an empty line. But the example you gave contains an empty line between the matches, so that would be something like this:

$ awk '/^$/{if (f) print; f=0}/foo/{f=1}f'
foo
line1
line2
line3

foo
line1
line2

Upvotes: 1

Related Questions