I need to edit several lines in a file such that if a line begins with (av or avpgw) then replace these with new text, else just insert the new text in beginning.
How can I do this using sed ?
I need to edit several lines in a file such that if a line begins with (av or avpgw) then replace these with new text, else just insert the new text in beginning.
How can I do this using sed ?
You can do it this way:
sed -e 's/^avpgw/new text/' -e t -e 's/^av/new text/' -e t -e 's/^/new text/' file
This replaces the pattern with new text
(s///) and jumps to the end (t). Otherwise it tries the next pattern. See also sed commands summary.
You can also separate the commands with ;
:
sed 's/^avpgw/new text/; t; s/^av/new text/; t; s/^/new text/' file
or put the commands in a sed command file:
s/^avpgw/new text/
t
s/^av/new text/
t
s/^/new text/
and call it this way:
sed -f commandfile file
If you want to ignore case, append an i at the end of the substitute command as in s/^av/new text/i
. Another way is to spell it out with character sets s/^[aA][vV]/new text/
. But that is not sed
specific, for this you can search for regular expressions in general.
This might work for you (GNU sed):
sed -r 's/^av(pgw)?.*/replacement/;t;s/^/replacement /' file
My answer is but a minor clarification to Olaf's excellent solution above.
If you are using OSX (which for me, using Catalina, uses a 2005 non-GNU version of sed
), and you try to use his more-concise semicolon-based solution (repeated below, tiny modification with the 1/2/3's at the end):
sed 's/^avpgw/new text 1/; t; s/^av/new text 2/; t; s/^/new text 3/' file
... you may get an error similar to the below, due to the use of the t
command in combination with the semicolons [;
] (which are themselves separated from the rest of the command by regular spaces):
sed: 1: "s/^avpgw/new text 1/; t ...": undefined label '; s/^av/new text 2/; t; s/^/new text 3/'
This problem, and a solution, is described in: sed “undefined label” on MacOS
Below is a version of Olaf's "all-in-one command" solution that works on OSX. It's debatable whether the \n
characters are really any better than just using extra -e
s. lolz aside: I'm mainly posting because I wanted to share the "root cause" of this problem so that people using OS X won't drive themselves crazy thinking that their sed
version doesn't properly support the t
command robustly -- it's just an issue of semicolons versus newlines, that's all!
Test file:
bash-3.2$ cat file
+ cat file
something
avpgw something else
av another thing
text
Original command, executed on OS X:
bash-3.2$ sed 's/^avpgw/new text 1/; t; s/^av/new text 2/; t; s/^/new text 3/' file
sed: 1: "s/^avpgw/new text 1/; t ...": undefined label '; s/^av/new text 2/; t; s/^/new text 3/'
With newlines instead of semicolons:
bash-3.2$ sed $'s/^avpgw/new text 1/\nt\ns/^av/new text 2/\nt\ns/^/new text 3/' file
new text 3something
new text 1 something else
new text 2 another thing
new text 3text