7

I'm parsing an XML file with

"lalala it's a Sunday {{ Some words here, maybe
a new line }} oh boy"

How would I use grep to get everything within "{{" and "}}" given that the grep . character doesn't recognize newlines?

Currently I have

grep '{{.*}}'

but it only works on things that are on the same line.

Phrogz
  • 296,393
  • 112
  • 651
  • 745
Rio
  • 14,182
  • 21
  • 67
  • 107

4 Answers4

8

One option is to remove the newline and then grep, as in:

 cat myfile | tr -d '\n' | grep {{.*}}

But if you say this is an XML file, why not use an XML parser that takes advantage of the file's inherent structure rather than just regexp?

EDIT

Grep regexp are greedy, you can use perl regexp:

cat myfile | tr -d '\n' | perl -pe 's/.*?({{.*?}})/\1\n/g' | grep {{

This should output one match per line. If you have nested {{ then this will get even more complicated.

Jesse Cohen
  • 4,010
  • 22
  • 25
  • 1
    It does the cat but now the grep doesn't work - it returns the entire file. What gives? – Rio Feb 20 '11 at 18:01
2

This is the way i solved that problem

   grep '{{[\s\S]*}}'
Yuri Barbashov
  • 909
  • 1
  • 6
  • 2
1

You can use alternation between mutually exclusive character sets to match truly any character. For example, this command:

grep -E "\{\{([[:digit:]]|[^[:digit:]])+\}\}"

...will match anything (greedily) between the first {{ and last }}.

But as @JesseCohen states, you really, really, really should be parsing XML with an XML parser, not regexps.

Community
  • 1
  • 1
Phrogz
  • 296,393
  • 112
  • 651
  • 745
  • If you must know, I'm trying to extract parts of a wikipedia dump XML file that contains unstructured data (all of the above potentially contained within ``). So I think the XML parsing is a bit less relevant here. – Rio Feb 20 '11 at 18:24
  • Wow, I did just that (the wikipedia dump thing). You might find it a lot harder than it seems (at least I did). – Noam Feb 20 '11 at 19:11
  • Moreover, I think using a XML parser requires to load all the file at once, and that Wiki dump is HUGE. – Noam Feb 20 '11 at 21:02
  • @Noam Not if it's a streaming SAX parser, e.g. http://nokogiri.org/Nokogiri/XML/SAX.html – Phrogz Feb 20 '11 at 21:11
0

This worked for me:

grep -zo '[[:cntrl:][:print:]]'
Peter K
  • 1,787
  • 13
  • 15