• Uncategorized

About linux : Search-for-a-String-and-retrieve-the-line-having-it-and-all-lines-following-it-until-another-specific-pattern

Question Detail

Using linux, I want to search a text file for the string Blah and then return the line full line that contained the string and all the lines following the pattern up until a line that contains the word Failed.

For example,

Test Case Name "Blah"
Error 1
Error 2
Error 3
Test Case Name "Foo"
Test Case Name "Red"

In the above, I want to search for “Blah”, and then return:

Test Case Name "Blah"
Error 1
Error 2
Error 3

Up until the line Failed. There can be any number of “Error” lines between Blah and Failed.

Follow up to make it faster

Both sed and awk options worked.

sed '/Blah/!d;:a;n;/Failed/d;ba' file


awk '/Failed/{p=0}/Blah/{p=1}p;' file

However, I noticed that while returning the expected outcome is quite fast, it takes ages to exit. Maybe these commands are recurrently searching for Blah and given that it appears only once, they run until the end-of-file.
This would not be much of a problem but I’m working with a file that contains 10 million lines and for now it is painfully slowly.

Any suggestions on how to exit after finding both lines containing Blah and Failed would be much appreciated.


Question Answer

With sed:

sed '/Blah/,/Failed/!d;//{1!d;}' file
  • /Blah/: match lines from Blahto Failed
  • !d: do not delete previous matching lines
  • //{1!d;}: from lines matching the addresses (that is Blahand Failed), do not delete the first one 1!d.

This might work for you (GNU sed):

sed -n '/Blah/,/Failed/{/Failed/!p}' file

Print the lines between and including Blah to Failed unless the line contains Failed.

    sed ':a;/Blah/!d;:b;n;/Failed/ba;bb' file

If a line does not contain Blah delete it. Otherwise, print the current line and fetch the next (n). If this line contains Failed delete it and begin next iteration. Otherwise, repeat until successful or end-of-file.

The first solution prevents Blah and Failed being printed if they inhabit the same line. The second alternative, allows this.

would you like do with awk?
awk '/Failed/{p=0}/Blah/{p=1}p;' file will works for you.

You may also like...

Leave a Reply

Your email address will not be published.

This site uses Akismet to reduce spam. Learn how your comment data is processed.