Link to home
Start Free TrialLog in
Avatar of ibanja
ibanja

asked on

using sed - how do I delete lines above and below a match?

using sed - I need to delete one line above and one line below any line with "ldots" on it.  

In the example below all of the lines with "\backslash" and all the lines with "\end_layout" have to be deleted.   There are other  lines with  "\end_layout" that need to stay so that's why I can't do something like:
sed -e 's/\\end_layout//'

Example:
$ grep -A1 -B1 ldots sampleDoc.lyx
\backslash
ldotsye
\end_layout
--
\backslash
ldotsforeordained
\end_layout
--
\backslash
ldotsAnd
\end_layout
--
\backslash
ldotsfor
\end_layout
--
\backslash
ldotsthat
\end_layout
--
\backslash
ldotsI
\end_layout
--
\backslash
ldotsboth
\end_layout
--
\backslash
ldotsleaving
\end_layout
--
\backslash
ldotsthat
\end_layout
--
\backslash
ldotsas
\end_layout

An explanation of the arguments would be appreciated.  I've been trying to make sense of these sed one-liners to apply to my problem.

# print 1 line of context before and after regexp, with line number
# indicating where the regexp occurred (similar to "grep -A1 -B1")
sed -n -e '/regexp/{=;x;1!p;g;$!N;p;D;}' -e h

# print the line immediately before a regexp, but not the line
 # containing the regexp
 sed -n '/regexp/{g;1!p;};h'

 # print the line immediately after a regexp, but not the line
 # containing the regexp
 sed -n '/regexp/{n;p;}'

Thanks,
Frank
Avatar of ozo
ozo
Flag of United States of America image

do you want
sed -n '/ldot/p'
Avatar of ibanja
ibanja

ASKER

No, because I need the rest of the file.  I only want to delete the lines above and the lines below a match.

Example: I want to take this:
line one
line two

\backslash
ldotsleaving
\end_layout

last line

and turn it into this:
line one
line two

ldotsleaving

last line

Thanks
try

sed -e 'g/ldots/-1,+1d'
I'd use perl or awk instead:
awk '(s==1){s=0;next}{x++}/ldots/{x--;s=1}{a[x]=$0}END{for(x in a){print a[x]}}' yourfile
ASKER CERTIFIED SOLUTION
Avatar of DocGyver
DocGyver
Flag of Afghanistan image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of ibanja

ASKER

ahoffmann,

thanks for the input but I could not get this to work.  It was scrambling the document somehow.  I created a short sedTest doc by running "grep -A1 -B1 ldots sampleDoc.lyx > sedTest" which produces the exact same output as in my original question - dumped to the file named sedTest. I then ran line that you gave and got the following:

$ awk '(s==1){s=0;next}{x++}/ldots/{x--;s=1}{a[x]=$0}END{for(x in a){print a[x]}}' sedTest
ldotsthat
--
--
ldotsAnd
ldotsas
--
ldotsfor
--
ldotsthat
--
ldotsI
--
ldotsboth
--
ldotsye
ldotsleaving
--
--
ldotsforeordained
Avatar of ibanja

ASKER

DocGyver,

That is perfect.  It works and thanks so much for the explanation.  That clearifies a few questions I have had about how to use some of the options in sed, especially the h and the n.  I could never get them to work and didn't have any good examples to compare to.

Much appreciated,
Frank
you got a solution, perfect.
According my suggestion, the result you posted is exactly what it should do as I understand it from your description.
Avatar of ibanja

ASKER

ahoffmann,

"According my suggestion, the result you posted is exactly what it should do as I understand it from your description."

Sorry, I might have to be more clear.  Thanks though.