0

My problem is the same as it's here, except I only want the first occurrence, ignore all the rest:

How to use sed/grep to extract text between two words?

In his example if it would be:

 input: "Here is a String Here is a String"

But I only care about the first "is"

echo "Here is a String Here is a String" | grep -Po '(?<=(Here )).*(?= String)' 

output: "is a String Here is a"

Is this even possible with grep? I could use sed as well for the job.

Thanks

Community
  • 1
  • 1
Codi
  • 1
  • 1
  • 2
  • 1
    If you want to find lines containing a pattern, use `grep` -- or `egrep`. If you want to find lines containing a pattern and then transform it in some way before printing the result, use `sed`. – Ned Jan 26 '14 at 20:49

3 Answers3

1

Your regexp happens to be matching against the longest string that sits between "Here" and "String". That is, indeed, "Here is a String Here is a String". This is the default behaviour of the * quantifier.

$ echo "Here is a String Here is a String" | grep -Po '(?<=(Here )).*(?= String)'
is a String Here is a

If you want to match the shortest, you may put a ? (greediness modifier) just after the * quantifier:

$ echo "Here is a String Here is a String" | grep -Po '(?<=(Here )).*?(?= String)'
is a
is a
etuardu
  • 5,066
  • 3
  • 46
  • 58
0

To get the first word you can use grep -o '^[^ ]*':

echo "Here is a String Here is a String" | grep -Po '(?<=(Here )).*(?= String)' | grep -o '^[^ ]*'

And you can pipe grep to grep multiple times to compose simple commands into complex ones.

fede1024
  • 3,099
  • 18
  • 23
0
sed 's/ String.*//;s/.*Here //'
Kent
  • 189,393
  • 32
  • 233
  • 301