5

Is there a way to do:

output | grep "string1" | grep "string2" 

BUT with awk, WITHOUT PIPE?

Something like:

output | awk '/string1/ | /string2/ {print $XY}'

Result should be subset of matches, if tha makes sense.

2 Answers2

11

The default action with awk is to print, so the equivalent of

output | grep string1 | grep string2

is

output | awk '/string1/ && /string2/'

e.g.

$ cat tst
foo
bar
foobar
barfoo
foothisbarbaz
otherstuff

$ cat tst | awk '/foo/ && /bar/' foobar barfoo foothisbarbaz

  • 1
    Accepting this answer because of the extra example/ proof – RiddleMeThis Dec 30 '20 at 16:06
  • That is the equivalent of the pipeline the OP provided but if the OP actually wants to match 2 strings instead of 2 regexps then it'd be awk 'index($0,"string1") && index($0,"string2") – Ed Morton Jan 02 '21 at 18:31
5

If you want awk to find lines that match both string1 and string2, in any order, use &&:

 output | awk '/string1/ && /string2/ {print $XY}'

If you want to match either string1 or string2 (or both), use ||:

 output | awk '/string1/ || /string2/ {print $XY}'
terdon
  • 242,166
  • 1
    Just to note, for anyone who stumbles upon this, what I exactly did was: ps aux | awk ... to keep awk from showing in the result I had to do awk /[s]tring/. Its the same trick used for grep. – RiddleMeThis Dec 30 '20 at 15:12
  • 2
    I think the {print $XY} thing is something like a placeholder that the OP thought would be useful/necessary. I believe it is better out of the answer since it doesn't make much sense. – Quasímodo Dec 30 '20 at 15:34
  • @Quasímodo it makes perfect sense: it is a placeholder for "print field number N" and including it shows what the correct syntax would be, so it can easily be adapted by future users. – terdon Jan 01 '21 at 14:37