Take the 2-minute tour ×
Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems.. It's 100% free, no registration required.

I'm looking to do a find and replace within a giant database dump, and it's not doing what I think should happen. I'd like to grep for my target string in the file, and then see the surrounding 8 characters or so (I might need to adjust that number, depending). How can I do that?

The reason I can't eyeball this is because there are many hundreds, if not thousands of matches. I want to get some number of characters surrounding the string, and then pipe it into uniq or something to see why my find and replace is having unexpected behaviors.

Also, there can be multiple matches on the same line!

share|improve this question
    
It is not a text file? –  enzotib Aug 24 '11 at 20:03
    
It is, but even just the matches are too big a file to eyeball. –  user394 Aug 24 '11 at 20:08

2 Answers 2

up vote 8 down vote accepted

The crude way using grep would be something like

grep -o "....yourtext...." /path/to/the/dump.sql

The number of dots corresponds to the number of characters before/after the grepped text. The -o option makes grep output only the matches, not the whole lines.

To use uniq on the output, remember you have to sort the output first. So typically, you'd do

grep . . . | sort | uniq

If you are interested in the hitcount for each match, you can get nice output using

grep . . . | sort | uniq -c | sort -n
share|improve this answer
    
Crude? Utterly sophisticated! –  user394 Aug 24 '11 at 20:40
1  
You could expand on this a little by using the repeat operator: grep -o '.\{8\}yourtext.\{8\}'. This is a little less dizzying than counting 8 dots. –  Caleb Aug 24 '11 at 20:44
    
:) By crude I mean you don't play with things like counting matched characters (using ranges) or narrowing the character sets. –  rozcietrzewiacz Aug 24 '11 at 20:46
    
@Caleb and user394: This is exactly what I intended not to suggest (and thus called my method "crude"). One does not need to remember the repeat operator construct, besides - it is even faster to type "....." than ".\{6\}". –  rozcietrzewiacz Aug 24 '11 at 20:51

Starting from the answer of @rozcietrzewiacz, I can expand to

pattern="string"
num=8
grep -on ".\{0,$num\}$pattern.\{0,$num\}" input-file
share|improve this answer
    
The "crude" dot sequence is looking better and better all the time :) –  Caleb Aug 24 '11 at 21:30
1  
@Caleb: generally the "crude" answer is a good start, but sometimes one want to elaborate a little bit on it. –  enzotib Aug 25 '11 at 5:47
1  
The dot sequence method won't find left or right justified target patterns; this method will. (+1) –  Peter.O Aug 25 '11 at 12:07
2  
PS.. I just noticed that it won't catch multiples instances of pattern on the same line (as the OP mentioned) when the scope of the trailing 'exta' text of the first pattern overlaps the scope of the leading 'extra' text of the next pattern –  Peter.O Aug 25 '11 at 12:18
    
@fred: yeah, -o gives only the first match when two matches overlap: echo 'aaabbbccc' | grep -o 'bb –  enzotib Aug 25 '11 at 12:48

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.