Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems. Join them; it only takes a minute:

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

For a large logging file, how do I display those lines without "success" or not terminated with "ok"?

share|improve this question
6  
grep -Ev '(success|ok$)' – jordanm Mar 2 at 18:48
    
@jordanm was going to suggest the same. This is an answer though and should be put in the right section. – val0x00ff Mar 2 at 18:59
    
@jordanm terrific, please make it an answer – Lee Mar 2 at 19:19
up vote 13 down vote accepted

To remove lines that contain either string, specifically with grep:

  • In one command, per jordanm's comment:

    grep -Ev 'success|ok$'
    

    or:

    grep -ve success -e 'ok$'
    

    or:

    grep -v 'success
    ok$'
    
  • In two commands:

    grep -v success file | grep -v 'ok$'

Example:

$ cat file
success something else
success ok
just something else

$ grep -Ev 'success|ok$'
just something else
$ grep -v success file | grep -v 'ok$'
just something else

To remove lines that contain both strings, specifically with grep:

grep -v 'success.*ok$' file

Example:

$ cat file
success something else
success ok
just something else

$ grep -v 'success.*ok$' file
success something else
just something else
share|improve this answer
    
if jordanm wants to answer instead, I'll delete this one. – Jeff Schaller Mar 2 at 19:15
    
No, this is fine. – jordanm Mar 2 at 19:21
1  
Lee, I see you've accepted this answer, but I want to clarify - these greps will remove lines that contain either of those two strings; did you want to remove only lines that contain both "success" and end with "ok" ? – Jeff Schaller Mar 2 at 19:43
    
No. either, not both. – Lee Mar 2 at 19:58
    
thanks for clarifying; take a look at the most recent edit to your question to make sure it says what you meant. – Jeff Schaller Mar 2 at 20:00

I would try awk

awk '/success/ { next ; } /ok$/ { next ; } { print ;}' file

where

  • /success/ { next ; } find word success and skip line
  • /ok$/ { next ; } find lower case ok and skip line
  • { print ;} implicit else : print line

as per suggestion

short awk (thanks to Stéphane Chazelas )

awk '!/success/ && !/ok$/'

which is basically not (success) and not (ok at end of line )

golfed awk (thank to cas )

awk '! /success|ok$/'

which reuse regexp, and negate it

share|improve this answer
    
Even if this works, that's not an answer to the question. – Quora Feans Mar 2 at 18:57
1  
Yes, it's an alternative way. – Lee Mar 2 at 19:25
    
@Lee: it's not an alternative. It does not fulfill the condition "use grep to." – Quora Feans Mar 2 at 19:31
4  
awk '!/success/ && !/ok$/' would be more canonical. – Stéphane Chazelas Mar 2 at 22:00
1  
or even awk '! /success|ok$/' – cas Mar 3 at 1:27

Adding to grep -Ev commands above: You can use egrep -v 'success|ok$' filename

share|improve this answer
1  
egrep is deprecated in favor of grep -E – Dani_l Mar 3 at 11:39

Since awk was mentioned, another alternative would be sed:

sed '/success/d;/ok$/d' file
sed -e '/success/d' -e '/ok$/d' file

or (Newer sed and future POSIX) thanks to Stéphane Chazelas

sed -E '/success|ok$/d' file
share|improve this answer
1  
If you change sed -r to sed -E, then that will work in some BSD sed in addition to (not too old versions of) GNU sed. sed -E will be in the next major issue of the POSIX spec. – Stéphane Chazelas Mar 3 at 10:06

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.